前端路由详解

前端路由与单页页面
路由就是指随着浏览器地址栏的变化,展示给用户的页面也不相同。
传统的网页根据用户访问的不同的地址,浏览器从服务器获取对应页面的内容展示给用户。这样造成服务器压力比较大,而且用户访问速度也比较慢。在这种场景下,出现了单页应用。
单页应用(spa),就是只有一个页面,用户访问一个网址,服务器返回的页面始终只有一个,不管用户改变了浏览器地址栏的内容或者在页面内发生了跳转,服务器不会重新返回新的页面,而是通过相应的js操作来实现页面的更改。而地址栏内容的改变,显示不同的页面,实现的手段就是前端路由。

前端路由是现代SPA应用必备的功能,每个现代前端框架都有对应的实现,例如vue-router、react-router。
我们不去探究vue-router或者react-router们的实现,因为不管是哪种路由无外乎用兼容性更好的hash实现或者是H5 History实现,与框架几个只需要做相应的封装即可。
前端路由的简单实现方式
我们经常在 url 中看到 #,这个 # 有两种情况,一个是我们所谓的锚点,比如典型的回到顶部按钮原理、Github 上各个标题之间的跳转等,但是路由里的 # 不叫锚点,我们称之为 hash。
现在的前端主流框架的路由实现方式都会采用 Hash 路由,本项目采用的也是。
当 hash 值发生改变的时候,我们可以通过 hashchange 事件监听到,从而在回调函数里面触发某些方法。。
hash+hashchange实现
这种方法的好处在于支持IE浏览器。对早期的一些浏览器的支持比较好。
实现原理:
location.hash始终指向页面url 中#之后的内容
当当前页面的url =’www.baidu.com’,可以在浏览器的控制台输入location.hash为空,当页面指向url =’www.baidu.com/#/hello’的时候,location.hash = ‘#/hello’。通过读取location.hash可以知道当前页面所处的位置。通过hashchange事件可以监听location.hash的变化,从而进行相应的处理即可。
那么如何触发hash的改变呢?这里主要由两种方法:
设置a标签,href = ‘#/blue’,当点击标签的时候,可以在当前url的后面增加上’#/blue’,同时触发hashchange,再回调函数中进行处理。
另外 直接在js中对location.hash = ‘#/blue’即可,此时url会改变,也会触发hashchange事件。

下面我们自己实现一个前端路由

  <a href="#/home" class="router">home</a>
    <!-- 导航 -->
    <div class="router_box">
        <a href="#/home" class="router">主页</a>
        <a href="#/news" class="router">新闻</a>
    </div>
    <!-- 页面中显示内容的部分 -->
    <div id="router-view"></div>

        // 配置不同的路由 要显示的页面内容
        let routes = [{
     
            path: '#/home',
            page: `
                <h1>我是首页</h1>
                `
        }, {
     
            path: '#/news',
            page: `
                <h1>我是新闻页面</h1>
                `
        }]

        // 监听hashchange 变化,一旦有变化,意味着可能要改变页面显示的内容
        window.addEventListener("hashchange", () => {
     
            // 获取变化以后的hash
            let nowHash = window.location.hash;
            console.log(nowHash)
            // 去路由配置中查找是否配置过这个路由,并找到这个路由配置
            let routeConfig = routes.find((item, index) => {
     
                return nowHash == (item.path);
            });
            console.log(routeConfig)
            if (routeConfig) {
     
                // 如果存在这个配置 就把配置中要显示的内容显示到页面上
                document.querySelector("#router-view").innerHTML = routeConfig.page;
            }
        });

把上面的代码封装一下

  class MyVueRouter {
     
        constructor({
     
            routes
        }) {
     
            // 监听hashchange 变化,一旦有变化,意味着可能要改变页面显示的内容
            window.addEventListener("hashchange", () => {
     
                // 获取变化以后的hash
                let nowHash = window.location.hash;
                console.log(nowHash, routes)
                // 去路由配置中查找是否配置过这个路由,并找到这个路由配置
                let routeConfig = routes.find((item, index) => {
     
                    return nowHash == (item.path);
                });
                console.log(routeConfig)
                if (routeConfig) {
     
                    // 如果存在这个配置 就把配置中要显示的内容显示到页面上
                    document.querySelector("#router-view").innerHTML = routeConfig.page;
                }
            });
        }

    }
    let router = new MyVueRouter({
     
        routes: [{
     
            path: '#/home',
            page: `
            <h1>我是首页</h1>
            `
        }, {
     
            path: '#/news',
            page: `
            <h1>我是新闻页面</h1>
            `
        }]
    })

你可能感兴趣的:(html,html)