基于react的hash路由简易实现

基于react的hash路由简易实现

背景介绍

在SPA项目中,如果展示页面繁多,根据前端工程化理论中组件化思想,我们通常会将不同的页面,按照功能,职责等进行划分。 这个时候,每个页面,就需要一个相应的路由去对应。

现在react社区中已经有react-router这个成熟的轮子,我们可以直接引入并使用。

但具体hash路由是如何实现的,我们现在就来探讨一下...

在路由设计中,我们用到了设计模式中的 单例模式 观察者模式 中介者模式

所以如果有该设计模式基础或实践的小伙伴,会更容易看懂一些...

开始

首先我们要了解一下,监听路由改变,其实是监听2个事件并操作回调,进行渲染:

  1. 页面加载事件(window.onload)
  2. 页面url中hash部分改变事件(window.onhashchange)

原生html代码编写

<!doctype html>
<html>
	<head>
		<title>hash-router</title>
	</head>
	<body>
		<ul>
			<li><a href="#/">home</a></li>
			<li><a href="#/login">
					login
					<ul>
						<li><a href="#/login/login1">login1</a></li>
						<li><a href="#/login/login2">login2</a></li>
						<li><a href="#/login/login3">login3</a></li>
					</ul>
				</a></li>
			<li><a href="#/abort">abort</a></li>
		</ul>
		<div id = "content"></div>
	</body>
</html>
复制代码

在这里 我们指定了一系列路由,包括"#/","#/login"等。然后,我们就要针对页面onload事件和点击每个a标签之后hash改变事件来进行处理了。

原生js代码编写

创建一个HashRouter类
<script type = 'text/javascript'>
	"use strict"
	class HashRouter{
		constructor(){
			this.routers = {},
			this.init();
		}
	}
</script>
复制代码
  1. 在这段代码中 我们创建了一个HashRouter类,并且指定了一个routers空对象来存储路由信息。
  2. 将来在这个routers对象中,我们存储路由的名称及回调,如routers = { "#/login" : [ callback1, callback2 ] }。键名为hash路由名称,键值为数组,数组内为跳转到该路由所要执行的回调方法。
  3. 现在,我们来执行init方法,当HashRouter类被创建的时候,我们需要执行的一些初始化方法
当HashRouter类被创建时,执行的初始化方法
<script type = 'text/javascript'>
	"use strict"
	class HashRouter{
		constructor(){
			this.routers = {},
			this.init();
		}
		trigger(){
			//取出当前url中的hash部分,并过滤掉参数
			let hash = window.location.hash && window.location.hash.split('?')[0];
			//在routers中,找到相应的hash,并执行已保存在其中的回调方法
			if(this.routers[hash] && this.routers[hash].length > 0){
				for(let i = 0 ; i < this.routers[hash].length ; i++){
					this.routers[hash][i]();
				}	
			}
		}
		init(){
			window.addEventListener('load', () => this.trigger(), false);
			window.addEventListener('hashchange', () => this.trigger(), false);
		}
	}
</script>
复制代码

兼听了页面加载时和hash改变时事件,并针对改变事件做回调处理,即trigger方法

需要抛出api,让开发者添加监听事件回调

在上一步我们进行了初始化,监听了页面hash改变的事件并做相应的处理。但是,我们需要执行的回调方法,需要开发人员手动添加才行。

<script type = 'text/javascript'>
	"use strict"
	class HashRouter{
		constructor(){
			this.routers = {},
			this.init();
		}
		listen(path, callback){
			//如果routers中已经存在该hash,则为它pushcallback方法,否则新建一个相应数组,并push回调方法
			if(!this.routers[path]){
				this.routers[path] = [];	
			}
			this.routers[path].push(callback);
		}
		trigger(){
			//取出当前url中的hash部分,并过滤掉参数
			let hash = window.location.hash && window.location.hash.split('?')[0];
			//在routers中,找到相应的hash,并执行已保存在其中的回调方法
			if(this.routers[hash] && this.routers[hash].length > 0){
				for(let i = 0 ; i < this.routers[hash].length ; i++){
					this.routers[hash][i]();
				}	
			}
		}
		init(){
			window.addEventListener('load', () => this.trigger(), false);
			window.addEventListener('hashchange', () => this.trigger(), false);
		}
	}
<
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值