手擼vue-router 更好的理解vue-router的原理
阿新 • • 發佈:2022-03-19
從vue中引入需要使用的api
import { ref, inject } from "vue";
1. 定義全域性提供router資料的key
const ROUTER_KEY = "__router__";
2. createRouter:建立一個router, 接收傳入的options,並且return出去一個 Router例項,Router物件通過傳入的options例項化自己
function createRouter(options) {
return new Router(options);
}
3. useRouter 開發人員通過呼叫useRouter函式來拿到全域性提供的Router物件
function useRouter() {
return inject(ROUTER_KEY);
}
4. createWebHashHistory
通過呼叫createWebHashHistory來建立一個History路由 這個方法返回了bindEvents函式用來繫結hashchange,路由改變時觸發 同時返回了url,值為初始值function createWebHashHistory() { return { bindEvents: (fn) => { window.addEventListener("hashchange", fn); }, url: window.location.hash.slice(1) || "/", }; }
5. Router物件
options物件上包含開發人員傳入的引數:{
history:createWebHashHistory()
routes
}
可以看到history的值是呼叫了createWebHashHistory函式,拿到了返回值並傳給createRouter routes則是路由列表
再看Routes函式內部,通過內部變數儲存了history, routes, currrent 而current通過vue提供的ref api把history.url值拿過來儲存起來 current為響應式資料 這裡history.url有點繞,建議多看幾遍程式碼
最後呼叫history上面的bindEvents方法,註冊一個函式,在路由改變觸發hashchange事件時,更新current
最後install方法 在vue.use時會呼叫install方法進行元件註冊,這時使用最頂層元件app.provide提供資料給任意子元件使用 子元件通過useRouter方法獲取
通過在install方法中全域性註冊router-link元件和router-view元件
class Router {
constructor(options) {
this.history = options.history;
this.routes = options.routes;
this.current = ref(this.history.url);
this.history.bindEvents(() => {
this.current.value = window.location.hash.slice(1);
});
}
install(app) {
app.provide(ROUTER_KEY, this);
app.component("router-link", RouterLink);
app.component("router-view", RouterView);
}
}
6. 最後匯出api提供給開發人員使用
export { createRouter, createWebHashHistory, useRouter }
完整程式碼
下兩篇文章:RouterLink,RouterView