blog

Vueの初回レンダリングプロセス

2.レンダリングオプションがあるかどうかを判断し、レンダリングオプションがない場合は、テンプレートテンプレートは、レンダリング関数にコンパイルされたテンプレートから取り出され、DOMをレンダリングし、...

Feb 26, 2020 · 8 min. read
シェア

最近、Vueのソースコードの研究では、その後、主にVueの最初のレンダリングの要約を行うには〜〜。

まずは下の写真をご覧ください。

Vueのソースコードのアドレス、ここでは主にソースコードの下のsrcディレクトリを見てください。

I. エントリーファイルから

で定義されています。 src/platform/web/entry-runtime-with-compiler.js

次に、Vueの初期化処理です。

1.まず、Vueの$mountを削除し、$mountを書き換えて、$mountに新しい関数を追加します。

// src/platform/web/entry-runtime-with-compiler.js
// Vueインスタンスを $mount  
const mount = Vue.prototype.$mount
Vue.prototype.$mount = function (
 el?: string | Element,
 // ssrでない場合はfalse、ssrの場合はtrueを指定する。
 hydrating?: boolean
): Component {
 // elオブジェクトを取得する
 el = el && query(el)
 ...
}

2レンダリングオプションがあるかどうかを判断し、レンダリングオプションがない場合は、レンダリング関数にコンパイルされたテンプレートのテンプレートのうち、DOMをレンダリングし、マウントメソッドを呼び出します。

3.Vueにstatic compileメソッドが追加されました、役割はHTML文字列をrender関数にコンパイルすることです。

if (!options.render) {
 let template = options.template
 if (template) {
 ...
 }
}
Vue.compile = compileToFunctions
export default Vue

4.このファイルは、主にディレクティブとコンポーネントのVueのグローバル登録に拡張を介して、コンポーネントはTransitionとTransitionGroup、ディレクティブはv-modelとv-showであり、その後、Vueのプロトタイプに登録された_patch_関数は、_patch_関数は、仮想DOMを実DOMに変換する役割であり、_patch_関数は、実DOMに変換され、値を代入する_patch_関数は、ブラウザの環境を決定します5 Vueのコンストラクタを探し続けるブラウザの環境になります。patch_関数は仮想DOMを実DOMに変換するための関数で、patch関数に値を代入する際にブラウザ環境かどうかを判断します。 5引き続きVueのコンストラクタを探します。

extend(Vue.options.obj, platformDirectives);
extend(Vue.options.bar, platformComponents);
Vue.prototype.foo = inBrowser ? patch : noop;

"静的メンバの初期化"

6.src/core/index.jsでの定義

  • このファイルの initGlobalAPI(Vue) メソッドを呼び出して、Vue コンストラクタに静的メソッドを追加します。
src/core/global-api/index.js

7. initGlobalAPI(Vue)はexport function initGlobalAPI (Vue: GlobalAPI) { const configDef = {} configDef.get = () => config if (process.env.NODE_ENV !== 'production') { configDef.set = () => { warn( 'Do not replace the Vue.config object, set individual fields instead.' ) } } // Vue.config Object.defineProperty(Vue, 'config', configDef) // exposed util methods. // NOTE: these are not considered part of the public API - avoid relying on // them unless you are aware of the risk. // これらのツールやメソッドはグローバルApiの一部とはみなされないので、ある種のリスクを認識していない限り、これらに依存しないこと。 Vue.util = { warn, extend, mergeOptions, defineReactive } // 静的メソッド set/delete/nextTick Vue.set = set Vue.delete = del Vue.nextTick = nextTick // ... Vue.options._base = Vue // キープを設定する-alive extend(Vue.options.components, builtInComponents) // Vueを登録する.use()プラグインを登録する initUse(Vue) // Vueを登録する.mixin()ミキシンを実装する initMixin(Vue) // Vueを登録する.extend()入力されたオプションに基づいてコンポーネントのコンストラクタを返す initExtend(Vue) // Vueを登録する.directive(), Vue.component(), Vue.filter initAssetRegisters(Vue) }

  • Vueの初期化.config
  • キープアライブコンポーネントの設定
  • プラグインの登録 Vue.use()を使用してプラグインを登録します。
  • ミキシンを実装するためのVue.mixin()の登録
  • Vue.extend()を登録すると、渡されたオプションに基づいてコンポーネントのコンストラクタが返されます。
  • Vueの登録.directive(), Vue.component(), Vue.filter
src/core/instance/index.js

インスタンス・メンバーの初期化

  1. _init()
  • this._init(options)
  • function Vue (options) { if (process.env.NODE_ENV !== 'production' && !(this instanceof Vue) ) { warn('Vue is a constructor and should be called with the `new` keyword') } // _init() this._init(options) } // vmに登録する_init()メソッド, vmの初期化 initMixin(Vue) // vmに登録する$data/$props/$set/$delete/$watch stateMixin(Vue) // 初期化イベント関連メソッド //$on/$once/$off/$emit eventsMixin(Vue) // ライフサイクル関連のミキシンを初期化する // _update/$forceUpdate/$destroy lifecycleMixin(Vue) // render // $nextTick/_render renderMixin(Vue) export default Vue コンストラクタが定義され、メソッド
  • Vue 共通のインスタンス・メンバーの混在
initLifecycle(vm);
initEvents(vm);
initRender(vm);
callHook(vm, 'beforeCreate');
initInjections(vm);
initState(vm);
initProvide(vm);
callHook(vm, 'created');

インスタンス・メンバーの初期化 init()

  • 静的メンバとインスタンスメンバを初期化したら、Vueコンストラクタを呼び出し、_init()メソッドを呼び出します。
  • initはinitMixinで初期化されます。
_props/methods/_data/computed/watch

インスタンス・メンバーを初期化します initState()

vmの初期化 export function initState (vm: Component) { vm._watchers = [] const opts = vm.$options if (opts.props) initProps(vm, opts.props) if (opts.methods) initMethods(vm, opts.methods) if (opts.data) { initData(vm) } else { observe(vm._data = {}, true /* asRootData */) } if (opts.computed) initComputed(vm, opts.computed) if (opts.watch && opts.watch !== nativeWatch) { initWatch(vm, opts.watch) } }

initProps(vm, opts.props)
  • const props = vm._props = {} instance/state.jsで、まずVueインスタンスの$optionsを取得し、optionsにprops、メソッド、data、computed、watchプロパティがあるかどうかを判断し、ある場合はinitPropsで初期化します。initPropsは、Vueインスタンス用とpropsプロパティ用の2つのパラメータを受け取り、initProps関数にジャンプし、まずVueインスタンス用の_Propsオブジェクトを定義し、initProps関数に格納します。Vueインスタンスに1つ、propsプロパティに1つ。 initProps関数にジャンプして、まずVueインスタンス用の_Propsオブジェクトを定義し、それを定数として格納します。

    Object.defineProperty(target, key, sharePropertyDefinition);
  • 開発モードでは、この属性に直接値を代入すると、次のような警告が表示されます。

  • propsのプロパティはdefineReactiveによって本番環境で直接getとsetに変換されます。

  • プロキシでは、これはinitMethods(vm, opts.methods)

initMethods

  • で、Vueインスタンスとオプションのメソッドの2つのパラメータを受け取り、まずオプションのpropsを取得し、次にメソッドのすべてのプロパティを繰り返し、現在の環境が開発環境か本番環境かを判断します。 開発環境では、メソッドがfunciconかどうかを判断します。

initData(vm)

  • optionsにdataオプションがあると、initData(vm)が呼ばれます。

  • _dataプロパティobserve(vm._data = {}, true)observeはresponsiveの関数です。

  • initDataでは、optionsのdataオプションを取得し、dataオプションが関数かどうかを判断し、関数であれば、getData(data,vm)を呼び出し、dataのすべてのプロパティを取得し、propsとmethodsのすべてのプロパティも取得します。

const b = Object.keys(data);
const foo = vm.bar.obj;
const c = vm.bar.a;

最後にレスポンシブ処理を行います。


init関数の最後に$mountが呼ばれ、ページ全体がマウントされます。


最初のレンダリングプロセスの概要

  • 最初のレンダリングで、Vueはインスタンスと静的メンバで最初に初期化されます。
  • 初期化の終了時に、Vueのコンストラクタnew Vue()を呼び出すには、_init()メソッドと呼ばれるコンストラクタでは、このメソッドは、全体のVueの入口に相当します。
  • if (vm.bar.foo) { vm.obj(vm.bar.foo); }initメソッドでは、最後の呼び出し$マウント、2つの$マウントの合計は、最初のファイルで定義されている、つまり、エントランスのファイル$マウントは、コアの役割の$マウント()は、レンダリング関数にテンプレートをコンパイルするのに役立つことですが、それは最初の現在のレンダリングオプションが渡されるかどうかを判断します、渡されない場合は、テンプレートオプションを取得しに行きます、テンプレートオプションもない場合は、彼はテンプレートとしてelの内容を取り、その後、レンダリング関数にテンプレートをコンパイルするために、それは関数を介して、レンダリング関数にテンプレートをコンパイルするのに役立つことです。src/platform/web/entry-runtime-with-compiler.jsテンプレートオプションがない場合、彼はテンプレートとしてコンテンツをエルし、その後、テンプレートがレンダリング関数にコンパイルされ、それは関数を介して、レンダリング関数にテンプレートをコンパイルするのに役立ち、レンダリング関数がコンパイルされると、それはoptions.renderに存在するレンダリング関数になります。options.render関数に存在します。
  • entry-runtime-with-compiler.jscompileToFunctions()なぜなら、ランタイムバージョンの場合、elを取得しに行かないので、ランタイムバージョンの場合、runtime/index.jsの$mount()でelを再取得します。
  • src/platforms/web/runtime/index.js次にmountComponent()を呼び出します。このメソッドはmountComponent()で定義されており、最初にレンダーオプションを決定します。Vueのランタイムバージョンを使用していて、renderを渡さずにtemplateを渡した場合、ランタイムバージョンがコンパイラをサポートしていないことを伝えます。次にbeforeMountライフサイクルフックがトリガーされ、マウントが開始されます。
  • 次にupdateComponent()が定義され、vm._renderとvm._updateが呼び出されます。vm._renderは仮想DOMを生成し、vm._updateは仮想DOMを実際のDOMに変換してページにマウントします。
  • Watcher オブジェクトを作成するには、Watcher の作成時に updateComponent 関数を渡します。Watcher の内部では get メソッドが使用され、Watcher の作成が完了すると、マウントされたフック関数のライフサイクルがトリガされます。
  • マウントは終了し、最終的にVueインスタンスを返します。

上の図は、Vueが初めてレンダリングしたときの様子です。

ありがとうございました。

最後に、このコンテンツを読むためにあなたの貴重な時間を費やしていただきありがとうございます。もしこのコンテンツがあなたの役に立つと思われるなら、この記事に「いいね!」を押してください。

Read next