前端路由实现

1.基于hash路由模式
原理:hash路由模式,形如http://xxx.com/index#xx,#后面的xx就是hash值,一旦改变#的hahs值,不会发送请求,但会触发hashchange事件,因此可以通过监听hashchange事件来实现路由。
简单的demo

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>hash路由demo</title>
</head>
<body>
  <ul>
    <li><a href="#/">this is index</a></li>
    <li><a href="#/product">this is product</a></li>
    <li><a href="#/server">this server</a></li>
  </ul>
</body>
</html>
class HashRouter {
  constructor() {
    // 存储hash与callback键值对
    this.routes = {};
    // 保存当前的hash
    this.currentHash = '';

    // 绑定事件
    const hashChangeUrl = this.hashChangeUrl.bind(this);

    // 页面加载事件
    window.addEventListener('load', hashChangeUrl, false);
    // 监听hashchange事件
    window.addEventListener('hashchange', hashChangeUrl, false);
  }
  // path路径和callback函数对应起来,并且使用 上面的this.routes存储起来
  route(path, callback) {
    this.routes[path] = callback || function() {};
  }
  hashChangeUrl() {
    /*
     获取当前的hash值
     location.hash 获取的值为:"#/a, 因此 location.hash.slice(1) = '/a' 这样的
    */
    this.currentHash = location.hash.slice(1) || '/';
    // 执行当前hash对应的callback函数
    this.routes[this.currentHash]();
  }
}
// 初始化
const Router = new HashRouter();
const body = document.querySelector('body');
const changeColor = function(color) {
  body.style.backgroundColor = color;
};
// 注册函数
Router.route('/', () => {
  changeColor('red');
});
Router.route('/server', () => {
  changeColor('green');
}); 
Router.route('/product', () => {
  changeColor('#CDDC39');
});

2.基于history路由模式
这种模式核心是借助history的pushState实现,window.pushState(state,data,path);pushState改变url但是不刷新,pushState会向history添加一个浏览记录,类似的函数有replaceState(state,data,path),该函数会替换history顶部的浏览记录。
需要注意的是调用history.pushState()或history.replaceState()不会触发popstate事件。只有在做出浏览器动作时,才会触发该事件,如用户点击浏览器的回退按钮(或者在Javascript代码中调用history.back()或者history.forward()方法)


<body>
    <ul>
        <li>
            <a href="/"> this is index</a>
        </li>
        <li>
            <a href="/a"> this is a</a>
        </li>
        <li>
            <a href="/b">this is b</a>
        </li>
    </ul>
</body>
在这里插入代码片class HistoryRoutes {
  constructor() {
    // 保存对应键和函数
    this.routes = {};
    
    // 监听popstate事件
    window.addEventListener('popstate', (e) => {
      const path = this.getState();
      this.routes[path] && this.routes[path]();
    });
  }
  // 获取路由路径
  getState() {
    const path = window.location.pathname;
    return path ? path : '/';
  }
  route(path, callback) {
    this.routes[path] = callback || function() {};
  }
  init(path) {
    history.replaceState(null, null, path);
    this.routes[path] && this.routes[path]();
  }
  go(path) {
    history.pushState(null, null, path);
    this.routes[path] && this.routes[path]();
  }
}

window.Router = new HistoryRoutes();
console.log(location.pathname);
Router.init(location.pathname);

const body = document.querySelector('body');

const changeColor = function(color) {
  body.style.backgroundColor = color;
};
// 注册函数
Router.route('/', () => {
  changeColor('red');
});
Router.route('/product', () => {
  changeColor('green');
}); 
Router.route('/server', () => {
  changeColor('#CDDC39');
}); 

const ul = document.querySelector('ul');
ul.addEventListener('click', e => {
  console.log(e.target);
  if (e.target.tagName === 'A') {
    e.preventDefault();
    Router.go(e.target.getAttribute('href'));
  }
});
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值