【Vue六六】路由的基本概念: hash模式(锚链接) history模式路由 Vue-router介绍 vue-router路由模式 404和重定位——嵌套路由 动态路由匹配 网路请求

🌕写在前面
🍊博客主页勇敢link牛牛
🎉欢迎关注:🔎点赞👍收藏⭐️留言📝
🌟本文由 勇敢link牛牛 原创,CSDN首发!
📆首发时间:🌹2022年9月03日🌹
🆕最新更新时间:🎄2022年9月03日🎄
✉️千万别让人偷了你的梦,梦想是你自己的。不要让别人左右你的决定。别人相信的事实,未必是你的。追逐过,你就知道别人认为不可能的事,是有可能的。只是我们未拼尽全力!!加油 宝子——异父异母的亲兄弟!
📠参考书籍:📚《Vue2》
🙏作者水平很有限,如果发现错误,请留言轰炸哦!万分感谢感谢感谢!


前端路由

路由的基本概念:

  • 路由的本质就是一种对应关系,根据不同的URL请求,返回对应不同的资源。那么url地址和真实的资源之间就有一种对应的关系,就是路由。
  • SPA(Single Page Application)单页面应用程序,基于前端路由而起:整个网站只有一个页面,通过监听地址栏中的变化事件,来通过Ajax局部更新内容信息显示、同时支持浏览器地址栏的前进和后退操作。

💚hash模式(锚链接)

hash模式兼容性很强,刷新浏览器,页面还会存在
hash模式,缺点:地址栏不优雅,有#存在,不利于seo,记忆困难

hash模式路由

<body>
    <ul>
        <li><a href="#/aa">aaaa</a></li>
        <li><a href="#/bb">bbbb</a></li>
    </ul>
    <h1></h1>
    <script>
        window.onload = ()=>{
            init();
        }
        const component={
            aa:function(){
                return `<div>aaaa信息</div>`
            },
            bb:function(){
                return `<div>bbb信息</div>`
            }
        }        
        function init(){
            document.querySelector("h1").innerHTML = component["aa"]();

        }
        let changeHanler = (e)=>{
            let hash = location.hash || "#/aa";
            console.log(location.hash);
            try {
                document.querySelector("h1").innerHTML = component[hash.slice(2)]();
                
            } catch (error) {
                document.querySelector("h1").innerHTML = `<h1>404</h1>`
                
            }
        }
        window.addEventListener("hashchange",changeHanler);
    </script>
</body>

💜history模式路由

<body>
    <ul>
        <li><a href="/aa">aaaa</a></li>
        <li><a href="/bb">bbbb</a></li>
    </ul>
    <h1></h1>
    <script>
        const component={
            aa:function(){
                return `<div>aaaa信息</div>`
            },
            bb:function(){
                return `<div>bbb信息</div>`
            }
        }   
        let changeHanler = (path)=>{
            try {
                document.querySelector("h1").innerHTML = component[path]();
                
            } catch (error) {
                document.querySelector("h1").innerHTML = `<h1>404</h1>`
                
            }
        }   
        init();
        function init(){
            document.querySelectorAll("a").forEach((node)=>{
                node.addEventListener("click",clickHandler)
            })
            changeHanler('aa')


        }
        
        
        function clickHandler(e){
            e.preventDefault();
            history.pushState({},null,this.href);/* 在地址栏中显示 */
            changeHanler(this.href.match(/\/(\w+)$/)[1]);
            console.log(this.href.match(/\/(\w+)$/)[1]);
        }
        window.addEventListener("popstate",function(e){/* 检测地址栏路由变化 */
            changeHanler(location.pathname.slice(1))
        })
       
       
    </script>
</body>

Vue-router介绍

Vue Router 是 Vue.js 官方的路由管理器。它和 Vue.js 的核心深度集成,让构建单页面应用变得易如反掌。包含的功能有:
 嵌套的路由/视图表
 模块化的、基于组件的路由配置
 路由参数、查询、通配符
 基于 Vue.js 过渡系统的视图过渡效果
 细粒度的导航控制
 带有自动激活的 CSS class 的链接
 HTML5 历史模式或 hash 模式,在 IE9 中自动降级
 自定义的滚动条行为

vue-router路由模式:3种

 hash: 使用 URL hash 值来作路由。支持所有浏览器,包括不支持 HTML5 History的浏览器。
 history: 依赖 HTML5 History API 和服务器配置。查看 HTML5 History 模式。
 abstract: 支持所有 JavaScript 运行环境,如 Node.js 服务器端。如果发现没有浏览器的 API,路由会自动强制进入这个模式。
在这里插入图片描述

安装

如果在vue-cli创建项目时没有勾选上vue-router选项,此时就需要手动的来安装它

npm i -S vue-router@3

3.3.3、Vue Router的基本使用
Vue Router的基本使用步骤:
在src下建立router文件夹index.js文件
 引入相关库文件
 VueRouter引入到Vue类中,以插件的方式添加
 定义路由组件规则并创建路由实例
 把路由挂载到Vue根实例中
 添加路由组件渲染容器,挂载点
router/index.js

import Vue from 'vue';
import VueRouter from 'vue-router';

import Home from "@/views/Home.vue";
/* 以插件的方式添加 */
Vue.use(VueRouter);

/* 实例化路由对象及配置路由表 */

const routes = [{
    // 匹配的路由
    path:'/home',
    // 匹配成功后需要渲染的组件
    component:Home
}];

const router = new VueRouter({
    mode:"history",/* 路由模式 */
    routes:routes,/* 路由规则表 */
});

export default router;

在入口文件引入router/index.js,给vue实例配置 router,关联起来;
在组件里面设置挂载点:<router-view/>

# 路由文件
import Vue from 'vue'
import VueRouter from 'vue-router'
Vue.use(VueRouter)
# 定义路由规则
const routes = [
  { path: '/foo', component: Foo },
  { path: '/bar', component: Bar }
]

# 创建路由实例
const router = new VueRouter({
  routes
})

# 挂载根实例
// 记得要通过 router 配置参数注入路由,
// 从而让整个应用都有路由功能
const app = new Vue({
  router
}).$mount('#app')

# html 挂载点:
<div>
	<router-view></router-view>
</div>

声明式导航

router-link声明式导航
它最后编译为html的a标签,在vue-router3版本中可以自定义设置。
to:string|"{path,query:{},params:{}}"=>目标地址
tag:默认编译生成a,可以自定义。
activeClass: 指定激活样式名称,默认名称为:router-link-active,然后在组件的style里设置样式:

<template>
    <div >
        {{msg}}
        <ul>
            <li><router-link to="/home" activeClass="active">home页面</router-link></li>
            <li><router-link :to="{path:'/home',query:{id:100}}" activeClass="active">home页面</router-link></li>
            <li><router-link to="/about" activeClass="active">About页面</router-link></li>
        </ul>
        <router-view/>
        <hr>
    </div>
</template>

<script>
export default {
   data(){
    return {
        msg:"父组件"
    }
   }
}   
</script>

<style lang="scss" scoped>
    .active{
        color:red
    }
</style>

编程式导航

利用router的api来实现跳转:

this.$router.push("/login");
this.$router.replace({ name:'user' , params: {id:123} });
this.$router.push({ path:"/login" });
this.$router.push({ path:"/login",query:{username:"jack"} });
this.$router.go( n );//n为数字  负数为回退

例如:
点击按钮,三秒后跳转。

<template>
    <div>
        <h1>About页面</h1>
        <button @click="goHome">点击跳转到home组件</button>
    </div>
</template>

<script>
export default {
    methods:{
        goHome(){
            setTimeout(()=>{
                // this.$router.push("/home");
                this.$router.push({
                    path:'/home',
                    query:{id:2000}
                })
            },3000)
        }
    }
}

使用编程式导航实现登录跳转
全局配置router,配置路由规则,声明式和编程式混用。

<template>
    <div>
        <h1>登录</h1>
        <label for="">账号:<input v-model="username"></label><br/>
        <label for="">密码:<input v-model="password"></label><br/>
        <button @click="login">点击登录</button>
    </div>
</template>

<script>
export default {
    data(){
        return {
            username:'',
            password:''
        }
    },
    methods:{
        login(){
            if(this.username == "admin"){
                alert("登录成功");
                this.$router.replace("/home");
            }else{
                alert("登录失败");
            }
        }
    }

}
</script>

404和重定向

redirect
路由是从上往下匹配的。当前面的都匹配不上的时候就来执行我们设定的一个路由。
404也一样,路由匹配成功后不在往下执行,而*是通配符。我们把这个放在最后,来表达未能找到页面。

/* 实例化路由对象及配置路由表 */
const routes = [{
    // 匹配的路由
    path:'/',
    // 重定向
    redirect:'/home'
},
{
    // 匹配的路由
    path:'*',
    component:Notfound
}]

编程式导航在跳转到有当前地址一致的url时会报错,但是这个报错不影响功能。
解决办法:
在路由入口文件idnex,js添加代码:


在跳转过程中有代码:location.href=''会刷新整个页面,(不考虑再多的什么动画,任务的啥的)清空浏览器缓存,不用考虑微任务还是宏任务。
三秒后跳转:

mounted(){
    setTimeout(() => {
         this.$router.push('/home');
     }, 3000);
}

在这里插入图片描述
利用setsetInterval,但是注意宏任务的清除。

 mounted(){  
        let n=1;
        this.dis = setInterval(() => {
            if(++n >3){
                this.$router.push('/home').catch(()=>{})/* 捕获错误 */
            }
            console.log(n);
        },3000);
    },
    beforeDestroy(){
        this.dis && clearInterval(this.dis)
    }

嵌套路由

套路由最关键在于理解子级路由的概念:

比如我们有一个/users的路由,那么/users下面还可以添加子级路由
如:> /users/index、/users/add等等,这样的路由情形称之为嵌套路由。

<div>
      <h1>后台管理系统</h1>
      <hr/>
      <!-- 嵌套路由,则一定要在父路由中添加对应的 挂载点 -->
      <router-view />
  </div>

路由嵌套配置:

{
    path:'/admin',
    component:Admin,
    children:[{
        path:"messageall",/* 里面就不用写这个斜杠 */
        component:Messageall
    },
    {
        path:"user",
        component:User
    }]
    
},

http://localhost:8081/admin/user
在这里插入图片描述
解决登录跳转的方式,一种是直接跳转,一步到位,一种是跳转之后再重定位。
一定要在父组件中写好挂载点。

动态路由匹配传参

动态路由参数
一定要先定义,后使用。

<li>
	<router-link to='/data/1'>新闻1</router-link>
</li>
<li>
	<router-link to='/data/2'>新闻2</router-link>
</li>
<li>
	<router-link to='/data/3'>新闻3</router-link>
</li>

对于这样的参数指定,路由规则可以编写Wie:

{
    path:'/data/:pid',
    component:Data
}
得到这个这个后面的值:
<h1>data详情页面-{{$route.params.pid}}</h1>
可以在组件的js里写网络请求来完成这个数据渲染。
let pid = this.$route.params.pid;
{
    path:'/data/:pid?',也就是说这里的pid可以不写
    component:Data
}

如果有请求字符串为:

http://localhost:8081/data/2?name=2189

那么在组件里可获取到这个数据:this.$route.query

mounted(){
    console.log(+this.$route.query.name);
    let pid = this.$route.params.pid;
    // 进行网络请求
    // this.msg = xxxxx
}

:名称 定义动态路由的传参数的方式,可以定义N个 /:a/:b/:c
动态数据网络请求

npm i -S axios

网路请求

封装组件http.js:

import axios from "axios";
axios.interceptors.response.use(
    res => res.data,
    err => Promise.reject(err)
);
axios.interceptors.request.use(config =>config);

/**
 * 进行ajax网络通信。
 * @param {string} url  网络请求地址
 * @returns Promise对象
 */
export const get = url => axios.get(url);
export const post = (url,data={}) => axios.post(url,data);
export const put = (url,data={})=>axios.put(url,data);
export const del = (url) =>axios.delete(url);

使用组件进行网络请求:

<template>
    <div>
        <h1>data详情页面-{{$route.params.pid || 1}}</h1>
        
        <!-- <div v-html="">{{msg.data}}</div> -->
        <template v-if="msg == null">
            <div>加载中</div>
        </template>
        <template v-else>
            <h2>{{msg.title}}</h2>
            <div v-html="msg.data"></div>
        </template>
    </div>
</template>

<script>
import {get} from '@/utils/http.js'

export default {
   
    data(){
        return {
            msg:null,
        }
    },
    menthods:{},
    async mounted(){
    webpack 中的 devServer 中的express 把public设置为静态资源了
        this.msg = await get("/mock/new.json");
    }
}
</script>

<style>

</style>

在这里插入图片描述

vue-router

详细后面更新(待更)

页面路由参数

页面传参
1.动态路由参数      this.$route.params
	地址栏简洁,安全性更高一些,需求先定义后使用,否则会访问不到路由
	/url/:参数1/:参数2/值/:参数3?
2.query字符串     this.$route.query
	无需先定义,直接可以使用,地址栏不太简洁,字段信息地址栏中可以见到   搜索
3.props隐式传递  在路由定义的地方 boolean|{}|()=>({})  ==> 组件中的props来接受

cookie/sessionStorage/localStorage来完成

导航守卫

拦截作用
1.全局守卫,每次切换都会执行
beforeEach((to,from,next)=>{
	// next一定要执行一次,不然后续的操作完成进行
  next()
})
beforeResolve
afterEach((to,from)=>{})
2.路由独享守卫
beforeEnter
3.组件内守卫
beforeRouteEnter
beforeRouteUpdate
beforeRouteLeave

路由元信息

它就是对于你所定义的路由进行额外的描述补充

路由懒加载

默认所有的路由对应的组件它都会打包到app.js文件中,这样就会有一个情况,app.js文件,随着路由的变多,而文件体积变大,影响打开的速度
路由懒加载完成
{
  component:()=>import('xxxx')
}
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

勇敢*牛牛

你的鼓励将是我创作的最大动力

¥2 ¥4 ¥6 ¥10 ¥20
输入1-500的整数
余额支付 (余额:-- )
扫码支付
扫码支付:¥2
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值