国产xxxx99真实实拍_久久不雅视频_高清韩国a级特黄毛片_嗯老师别我我受不了了小说

資訊專欄INFORMATION COLUMN

VUE - MVVM - part11 - Extend

cartoon / 2554人閱讀

摘要:所以方法,是對默認進行擴展,從而實現擴展。這里我用了這個庫提供的合并方法,用來合并兩個對象,并不會修改原對象的內容。測試符合我們的預期,方法也就實現了,下一步,實現父子組件。系列文章地址優化優化總結

看這篇之前,如果沒有看過之前的文章,移步拉到文章末尾查看之前的文章。

組件的擴展

Vue 中有 extend 方法可以擴展 Vue 的實例,在上一步中,有一些實現是必須要通過子父組件才能實現,而子組件相當于一個特殊的 Vue 實例,所以這步,我們先把這個擴展實例的方法實現。

我們先來看看官網對于 extend 方法的介紹:

使用基礎 Vue 構造器,創建一個“子類”。參數是一個包含組件選項的對象。

從后面一句和具體的使用方法可以得出其實是我們創建實例時,對于傳入參數的擴展。對于這個參入參數我們就叫它 options

我們接著往下想,既然這個 options 是能擴展的,那么原 Vue 類下,肯定保存著一個默認 options ,而創建 Vue 實例時,會把傳入的 options 和默認的 options 進行合并。

所以 extend 方法,是對默認 options 進行擴展,從而實現擴展。

mergeOptions

ok 有了思路,我們來實現它:

首先是默認的 options ,同時我們假設一個方法(mergeOptions)用來合并 options

let uid = 0

export class Vue extends Event {
    ···

    _init(options) {
        let vm = this
        // 為了方便引用合并的 options 我們把它掛載在 Vue 實例下
        vm.$options = mergeOptions(
            this.constructor.options,
            options,
            vm
        )
        ···
    }
}
// 默認的 options
Vue.options = {
    // 組件列表
    components: {},
    // 基類
    _base: Vue
}

接著我們來實現 mergeOptions

import R from "ramda"

export function mergeOptions(parent, child) {
    // data/methods/watch/computed
    let options = {}

    // 合并 data 同名覆蓋
    options.data = mergeData(parent.data, child.data)

    // 合并 methods 同名覆蓋
    options.methods = R.merge(parent.methods, child.methods)

    // 合并 watcher 同名合并成一個數組
    options.watch = mergeWatch(parent.watch, child.watch)

    // 合并 computed 同名覆蓋
    options.computed = R.merge(parent.computed, child.computed)

    return options
}

function mergeData(parentValue, childValue) {
    if (!parentValue) {
        return childValue
    }
    if (!childValue) {
        return parentValue
    }
    return function mergeFnc() {
        return R.merge(parentValue.call(this), childValue.call(this))
    }
}

// 由于 watcher 的特殊性,我們不覆蓋同名屬性,而是都保存在一個數組中
function mergeWatch(parentVal, childVal) {
    if (!childVal) return R.clone(parentVal || {})
    let ret = R.merge({}, parentVal)
    for (let key in childVal) {
        let parent = ret[key]
        let child = childVal[key]
        if (parent && !Array.isArray(parent)) {
            parent = [parent]
        }
        ret[key] = parent
            ? parent.concat(child)
            : Array.isArray(child) ? child : [child]
    }
    return ret
}

目前我們僅僅實現了 data/methods/watch/computed4options 中的內容,所以我們先合并這 4 項,由于 data/methods/computed3 項是具有唯一性(比如 this.a 應該是一個確定的值),所以采用同名屬性覆蓋的方式,而 watch 是當發生變化時候執行方法,所以所有注冊過的方法都應該執行,因而采用同名屬性的內容合并成一個數組。

這里我用了 ramda 這個庫提供的合并方法,用來合并兩個對象,并不會修改原對象的內容。

extend

ok 合并 options 的方法寫好了,我們接著來實現 extend 同過上面的分析,extend 函數僅僅是對默認 options 的擴展

Vue.extend = function (extendOptions) {
    const Super = this

    class Sub extends Super {
        constructor(options) {
            super(options)
        }
    }

    Sub.options = mergeOptions(
        Super.options,
        extendOptions
    )

    Sub.super = Super
    Sub.extend = Super.extend

    return Sub
}

同樣的我們使用 mergeOptions 來合并一下 options 即可,同時將 super 指向父類、獲取 extend 方法。

測試
import {Vue} from "./Vue.mjs"

let subVue = Vue.extend({
    data() {
        return {
            dataTest: 1
        }
    },
    methods: {
        methodTest() {
            console.log("methodTest")
        }
    },
    watch: {
        "dataTest"(newValue, oldValue) {
            console.log("watchTest newValue = " + newValue)
        }
    },
    computed: {
        "computedTest": {
            get() {
                return this.dataTest + 1
            }
        }
    }
})

let test = new subVue({
    data() {
        return {
            subData: 11
        }
    },
    methods: {
        subMethod() {
            console.log("subMethodTest")
        }
    },
    watch: {
        "subData"(newValue, oldValue) {
            console.log("subWatch newValue = " + newValue)
        }
    },
    computed: {
        "subComputed": {
            get() {
                return this.subData + 1
            }
        }
    }
})

console.log(test.dataTest)
// 1
console.log(test.subData)
// 11

console.log(test.computedTest)
// 2
console.log(test.subComputed)
// 12

test.methodTest()
// methodTest
test.subMethod()
// subMethodTest

test.dataTest = 2
// watchTest newValue = 2
test.subData = 12
// subWatch newValue = 12

console.log(test.constructor === subVue)
// true
console.log(subVue.super === Vue)
// true

ok 符合我們的預期,extend 方法也就實現了,下一步,實現父子組件。

系列文章地址

VUE - MVVM - part1 - defineProperty

VUE - MVVM - part2 - Dep

VUE - MVVM - part3 - Watcher

VUE - MVVM - part4 - 優化Watcher

VUE - MVVM - part5 - Observe

VUE - MVVM - part6 - Array

VUE - MVVM - part7 - Event

VUE - MVVM - part8 - 優化Event

VUE - MVVM - part9 - Vue

VUE - MVVM - part10 - Computed

VUE - MVVM - part11 - Extend

VUE - MVVM - part12 - props

VUE - MVVM - part13 - inject & 總結

文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。

轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/94796.html

相關文章

  • VUE - MVVM - part12 - props

    摘要:看這篇之前,如果沒有看過之前的文章,移步拉到文章末尾查看之前的文章。而該組件實例的父實例卻并不固定,所以我們將這些在使用時才能確定的參數在組件實例化的時候傳入。系列文章地址優化優化總結 看這篇之前,如果沒有看過之前的文章,移步拉到文章末尾查看之前的文章。 前言 在上一步,我們實現 extend 方法,用于擴展 Vue 類,而我們知道子組件需要通過 extend 方法來實現,我們從測試例...

    bluesky 評論0 收藏0
  • VUE - MVVM - part13 - inject & 總結

    摘要:通過裝作這些變化,我們實現了從而到達了數據變化觸發函數的過程。于此同時,我們還實現了來擴展這個可響應的結構,讓這個對象擁有了觸發和響應事件的能力。最后,根據我們的實現,這是最終的產出,一個框架,了解一下系列文章地址優化優化總結 看這篇之前,如果沒有看過之前的文章,移步拉到文章末尾查看之前的文章。 provide / inject 在上一步我們實現了,父子組件,和 props 一樣 pr...

    niuxiaowei111 評論0 收藏0
  • VUE - MVVM - part7 - Event

    摘要:事件是什么在標準瀏覽器中,我們經常使用來為一個添加一個事件等。仔細看這些情況,歸結到代碼中,無非就是一個行為或情況的名稱,和一些列的動作,而在中動作就是,一系列的動作就是一個函數的集合。 看這篇之前,如果沒有看過之前的文章,可拉到文章末尾查看之前的文章。 事件是什么? 在標準瀏覽器中,我們經常使用:addEventListener 來為一個 DOM 添加一個事件(click、mouse...

    xialong 評論0 收藏0
  • VUE - MVVM - part4 - 優化Watcher

    摘要:關于中的的實現,差不多也就這樣了,當然這僅僅是基礎的實現,而且視圖層層渲染抽象成一個函數。不同于中的實現,這里少了很多各種標記和應用標記的過程。 看這篇之前,如果沒有看過之前的文章,可拉到文章末尾查看之前的文章。 回顧 首先我們思考一下截止當前,我們都做了什么 通過 defineReactive 這個函數,實現了對于數據取值和設置的監聽 通過 Dep 類,實現了依賴的管理 通過 Wa...

    CoffeX 評論0 收藏0
  • VUE - MVVM - part1 - defineProperty

    摘要:在中關于如何實現在網上可以搜出不少,在看了部分源碼后,梳理一下內容。換個說法,當我們取值的時候,函數自動幫我們添加了針對當前值的依賴,當這個值發生變化的時候,處理了這些依賴,比如說節點的變化。 在 VUE 中關于如何實現在網上可以搜出不少,在看了部分源碼后,梳理一下內容。 首先,我們需要了解一下 js 中的一個 API :Object.defineProperty(obj, prop,...

    liukai90 評論0 收藏0

發表評論

0條評論

最新活動
閱讀需要支付1元查看
<