vue-router路由講解

此文章用來系統講解vue-router路由

  1. 安裝vue

    只介紹npm安裝
    npm install vue-router --save 項目所需依賴
    在main.js或者app.vue中導入
    import Vue from 'vue';
    import VueRouter from 'vue-router';
    Vue.use(VueRouter);
    如今你就能夠開始使用vue-router了
  2. 結構vue-router

    先來簡單的瞭解一下使用的結構,方便後面學習
    <router-link to="/foo">Go to Foo</router-link> 至關於a標籤
    <router-view></router-view> 這時用來渲染匹配到的路由組件的
    下面就是具體的路由設置了
    const app = new Vue({
        router: new VueRouter({
            routes: [
                {path: '/foo',component: Foo} //匹配到路由'/foo'後渲染組件Foo
            ]
        })
    }).$mount("#app")
    很簡單吧
  3. 動態路由匹配npm

    說簡單點,就是不一樣的路由值,訪問同一個組件
    例如:
        const router = new VueRouter({
            routes: [
                { path: '/user/:id', component: User }
            ]
        })
        在 '/user/' 後面跟個 :id 表示這時可選的,就是說無論id是啥,均可以訪問User組件
        而且這個id存放在this.$route.params中,而且能夠有多個這樣的可選值
    注意點: 在不一樣的路由值之間切換訪問相同的組件,是不會重複渲染的,可是能夠經過watch來作出響應
        const User = {
            watch: {
                '$route' (to,from) {
                    // 對路由變化作出響應
                }
            }
        }
        // 有沒有以爲這個寫法挺怪的,管他呢,能用就行O(∩_∩)O哈哈~
  4. 嵌套路由編程

    嵌套路由很簡單,就是匹配到某個路由值,渲染到一個組件,這個組件內部還有router-view,這時能夠傳遞第二段路由值,加以匹配,若是不傳遞,能夠設置一個空的二段路由值
    例子以下:
        const router = new VueRouter({
            routes: [{
                path: '/user/:id',component: User
            }]
        })
        /user/demo 這個路由值,能夠匹配到User組件,若是User組件是以下的
        const User = {
            template: `
                <router-view></router-view>
            `
        }
        那麼須要對路由配置作以下修改
        const router = new Router({
            routes: [
                {path: '/user/:id',component: User,
                 children: [
                     {path: '',component: UserHome},
                     {path: 'profile',component: UserProfile}
                 ]
                }
            ]
        })
  5. 編程式導航api

    簡而言之,就是,使用js來實現router-link的功能
    使用 router.push ,此方法和router-link如出一轍,回產生瀏覽記錄,有以下幾種形式,和router-link是等價的
        router.push('home')
        router.push({path: 'home'}) // 和上面等價
        router.push({name: 'user',params: {userId: 123}}) // 這個是命名路由,後面講
        router.push({path: 'register',query: {plan: 'private'}}) // '/register?plan=private'
    使用router.replace(location)
        和router.push類似,只不過這裏不會產生瀏覽記錄,沒卵用
    使用router.go(n)
  6. 命名路由瀏覽器

    命名路由是用來給懶人用的,給router-link傳遞to屬性,使用path很長,很難寫,因此,起個名字,方便寫
    當某個路由配置是
    const router = new VueRouter({
        routes: [
            {
                path: '/user/:userId',
                name: 'user',
                component: User
            }
        ]
    })
    正常人是這樣訪問的 <router-link :to="/user/123"></router-link>
    懶人是這樣訪問的 <router-link :to="{name: 'user',params: {userId: 123}}"></router-link>
    咦。。。,好像還要多輸入幾個字符,不對,這是裝逼用的
  7. 命名視圖app

    這個玩意兒就是當匹配到一個路由值,同時渲染多個組件,很簡單,看下面demo
    <router-view></router-view> //這個沒有起名的默認就是 default
    <router-view name="a"></router-view>
    <router-view name="b"></router-view>
    const router = new VueRouter({
        routes: [
            {
                path: '/',
                components: {
                    default: Foo,
                    a: Bar,
                    b: Baz
                }
            }
        ]
    })
    // 這樣同時就渲染出 Foo,Bar,Baz 三個組件了
  8. 重定向和別名異步

    這兩個概念也是很簡單的
    重定向就是當訪問一個路由值,定向到另一個路由值,此即以假亂真,簡單demo以下
    const router = new VueRouter({
        routes: [
            {path: '/a',redirect: '/b'}
        ]
    })
    別名就是起個其它的名字,其實方法的仍是這個路由
    const router = new VueRouter({
        routes: [
            {path: '/a',component: A,alias: '/b'}
        ]
    })
  9. HTML5 History模式函數

    這部份內容也是裝逼專用,就是把url中的/#去掉,變好看一點,須要把其餘不符合要求的路由值定位到主頁上來,要否則就直接404,官網說這個功能要後臺來實現,不過我以爲,能夠直接用路由鉤子實現,詳見後述
  10. 導航鉤子學習

    這個功能很強大,能夠在進行導航的過程的各個時間點作處理,很吊的
    有全局的,單個路由的,組件的
    1.先來看個全局的鉤子,註冊一個全局的before鉤子
    const router = new VueRouter({...});
    router.beforeEach((to,from,next) => {
        // 能夠註冊多個before,多個before之間是異步的,可是導航必須等到這些鉤子執行完成,纔開始
        // to 目標路由對象
        // from 當前路由對象
        // next 有以下幾種用法
        // next() 執行下一個鉤子函數,沒有鉤子,則to到目標路由
        // next(false) 不to了,直接留在from這個路由
        // next('/') 無論這個to了,另找了一個to
        // next方法必須調用,不調用就是死循環,當心你電腦內存爆了
        // 記得剛開始學這個,我差點把電腦砸了
    })
    註冊一個after鉤子,這個做用不大,畢竟路由都跳轉了,惟一的做用就是來看看而已
    router.afterEach(route => {
        // ...
    })
    2.單個路由的
    直接上demo了吧,簡單
    const router = new VueRouter({
        routes: [{
            path: '/foo',
            component: Foo,
            beforeEnter: (to,from,next) => {
                //...
            }
        }]
    })
    3.組件內的
    這個也簡單,不過比上面兩個稍有點區別,上demo吧
    const Foo = {
        template: '...',
        beforeRouteEnter (to,from,next) {
            // 這裏不能直接訪問當前實例this,由於實例尚未渲染,不過能夠經過next來訪問
            next(vm => {
                // ...
            })
        },
        beforeRouteUpdate (to,from,next) {
            // 多個路由值訪問同一個組件,來回切換,組件不會刷新,那麼上面的這個鉤子就沒有了,此時這個鉤子登場
        },
        beforeRouteLeave (to,from,next) {
            // 顧名思義,不介紹了
        }
    }
  11. 路由元信息

    這玩意兒就是一個flag,用於遍歷的時候找到特殊的路由,用處很小,這裏不介紹了,感興趣本身查去
  12. 過渡動效

    就是在切換路由的時候展現動畫,若是你懂vue的transition,這部份內容你根本就不用看,直接上手
    <transition>
        <router-view></router-view>
    </transition>
  13. 數據獲取

    在切換到其餘路由,其餘路由獲取數據有兩種方式,渲染完成以後獲取數據,渲染以前獲取數據
    1.渲染完成以後獲取數據
    正常人都是這麼幹的,就是在組件的created鉤子中寫api獲取數據,不作介紹了
    2.渲染以前獲取數據
    這個仍是很經典的,頗有實際價值
    在接下來要切換的組件中的beforeRouteEnter中獲取數據,數據獲取完成以後再渲染,再添加一個渲染動畫,感受棒棒噠
    在next(vm => {
        // 將獲取的數據放到實例上,上面介紹過了
    })
    上面這個也能夠經過監聽$route來實現,不過有點稍微延遲,不推薦使用
    watch: {
        $route(){
            ...
        }
    }
  14. 滾動行爲

    這個仍是有點用的,切換到一個新的路由組件時,控制頁面的位置
    藉助scrollBehavior方法,這個方法要寫在router實例中
    const router = new VueRouter({
        routes: [...],
        scrollBehavior (to,from,savedPosition) {
            savedPosition是點擊瀏覽器的前進後退按鈕才管用,下面列舉了幾種使用demo
            return {x: 0,y: 0}; 簡單的回到最頂部
            return savedPosition; 返回原先的位置
            if (to.hash) {
                return {selector: to.hash} 錨點定位
            }
        }
    })
  15. 懶加載

    將組件拆分,實現按需加載,有以下幾種方式,之後添加組件的話都這樣用
    1.把路由對應的組件拆分紅異步組件
    const Foo = resolve => {
        require.ensure(['./Foo.vue'], () => {
            resolve(require('./Foo.vue'))
        })
    }
    2.AMD
    const Foo = resolve => require(['./Foo.vue'], resolve)
    3.將多個組件打包到一個模塊中
    const Foo = r => require.ensure([], () => r(require('./Foo.vue')), 'group-foo')
    const Bar = r => require.ensure([], () => r(require('./Bar.vue')), 'group-foo')
    const Baz = r => require.ensure([], () => r(require('./Baz.vue')), 'group-foo')
相關文章
相關標籤/搜索