Easy to write with VueRouter plug-in
This paper is used to review their usual learning achievements. This article is aimed at students who have some Vue foundation. This article will hand write a simple VueRouter plug-in to implement the basic jump route. The explanation ideas of this paper:
- The application of original VueRouter is briefly analyzed and some questions are put forward.
- List the key points of a simple VueRouter
- Implement the simple VueRouter plug-in.
Analysis of the original VueRouter plugin
The use of VueRouter
Router. js In the routing configuration file
// The first step is to introduce the VueRouter plug-in
import VueRouter from'VueRouter'// Step 2 install the VueRouter plug-in
Vue.use(VueRouter)
// Step 3 define the route
const routes = [...]
// Step 4 Create a route instance
const router = new VueRouter({routes})
Copy the code
In the main. Js
// Import the router
import router from './router'
// Mount the router to the Vue instance
new Vue({
router,
render: h= > h(App)
}).$mount('#app')
Copy the code
The routing view app.vue was added
<template> <div id="app"> <div id="nav"> <! - routing hop connection - > < the router - link to = "/" > Home < / router - the link > | < the router - link to = "/ about" > about < / router - the link > < / div > <router-view></router-view> </div> </template>Copy the code
// Route jump
this.$router.push('/')
this.$router.push('/about')
Copy the code
Analysis:
-
Why do we use vue.use (VueRouter)?
-
Install the Vue plug-in. If the plug-in is an object, you must provide the install method. If the plug-in were a function, it would be used as the install method. When the install method is called, Vue is passed in as an argument.
This method needs to be called before calling new Vue().
When the install method is called multiple times by the same plug-in, the plug-in will only be installed once.
-
-
New VueRouter() we need to pass routes and other parameters as configuration items
- We need to pass options as a configuration item to implement the simple VueRouter plug-in
-
Why do I attach the Router to a Vue instance?
- Add router to root to access this.$router globally for routing operations
-
When adding a routing view, I use components. Why can I use these two components directly?
- Note The two components are registered globally
Implement simple VueRouter requirement analysis
Define what the simple VueRouter needs to do:
Three, code implementation
The first step is to build a framework according to the above ideas
let Vue
1. Define a class
class VueRouter {
New VueRouter({routes})
constructor(options) {
this.$options = options
// 3. Obtain the current route so that the template can be rendered based on the route
// To get the routing address, for example http://localhost:8080/#about, we just need about
const initial = window.location.hash.slice(1) | |'/'
// Listen for hash changes to get the current routing address
window.addEventListener('hashchange'.() = > [
this.current = window.location.hash.slice(1)]}}// Plugins for 3. vue. js should expose an install method. The first argument to this method is the Vue constructor,
VueRouter.install = (_Vue) = > {
Vue = _Vue
// 4. Register router-link and router-view components globally
Vue.component('router-link', {})
Vue.component('router-view'}, {})export default VueRouter
Copy the code
The basic framework is set up, but there is still a step missing from the detailed implementation of the padding, so that this.$router can be accessed anywhere.
Because new VueRouter({router}), how do we get router? The router must be fetched from the options passed in.
We could give it a try
VueRouter.install = (_Vue) = > {
Vue = _Vue
/ / new
consoleThe log ('this',this)
Vue.prototype.$router = this.$options.router
Vue.component('router-link', {})
Vue.component('router-view'}, {})Copy the code
Let’s take a run
This is undefined. We can see this in the use of the VueRouter above.
Vue.use(VueRouter)
const router = new VueRouter({routes})
// Import the router
import router from './router'
/ /!!!!!! VueRouter. Install = (_Vue) =>{} Vue instance is not created, _Vue is undefined
new Vue({
router,
render: h= > h(App)
}).$mount('#app')
Copy the code
So how do we solve this problem? We can use vue. mixin as a global mixin and wait until the Vue instance is created to add $router.
Vue.mixin({
beforeCreate() {
// Because it is global mixin, the router option is called on every component creation, but is passed in only when the root instance is created, so add the following to determine which to avoid multiple executions
if (this.$options.router) {
Vue.prototype.$router = this.$options.router
}
}
})
Copy the code
Step 2 Fill in the details
let Vue
class VueRouter {
constructor(options) {
this.$options = options
// To get the routing address, for example http://localhost:8080/#about, we just need about
const initial = window.location.hash.slice(1) | |'/'
console.log(initial)
// Listen for hash changes to get the current routing address
window.addEventListener('hashchange'.() = > [
this.current = window.location.hash.slice(1)]}}// Vue.js plug-ins should expose an install method. The first argument to this method is the Vue constructor,
VueRouter.install = (_Vue) = > {
Vue = _Vue
console.log('this'.this)
Vue.mixin({
beforeCreate() {
// Because it is global mixin, the router option is called on every component creation, but is passed in only when the root instance is created, so add the following to determine which to avoid multiple executions
if (this.$options.router) {
Vue.prototype.$router = this.$options.router
}
}
})
Vue.component('router-link', {
props: {
to: {
type: String.required: true}},render(h) {
return h(
'a',
{
attrs: {
href: The '#' + this.to
}
},
this.$slots.default
)
}
})
Vue.component('router-view', {
render(h) {
let componnent = null
const route = this.$router.$options.routes.find(
(route) = > route.path === this.$router.current
)
if (route) {
componnent = route.componnent
}
return h(componnent)
}
})
}
export default VueRouter
Copy the code
When we run it, we find that the navigation route address has changed, but we don’t re-render the view, we want to re-render the view every time the path changes, we think of the render function that is called to update the view every time the responsive data changes. So we also need to add, set the current route to the corresponding data. We can use vue.util. DefineReactive
class VueRouter {
constructor(options) {
this.$options = options
// To get the routing address, for example http://localhost:8080/#about, we just need about
const initial = window.location.hash.slice(1) | |'/'
/ /!!!!!! Defines the response properties of an object
Vue.util.defineReactive(this.'current', initial)
// Listen for hash changes to get the current routing address
window.addEventListener('hashchange'.() = > {
this.current = window.location.hash.slice(1)}}}Copy the code
Now you have a simple VueRouter plug-in. That’s all for today, ha ha ha!
Reference: Let’s have a lesson, Miss Yang
Vue official document