Der Inhalt dieses Artikels handelt von der ersten Rendering-Analyse 2 (reine DOM-Elemente). Ich hoffe, dass er für Sie hilfreich ist.
Im vorherigen Artikel haben wir vorgestellt, wie das Top-Level-Objekt ReactCompositeComponent[T] aufgebaut ist. Schauen wir uns als Nächstes an, was „batchedMountComponentIntoNode“ tut.
Der in diesem Artikel erläuterte Aufrufstapel sieht folgendermaßen aus:
|=ReactMount.render(nextElement, container, callback) ___ |=ReactMount._renderSubtreeIntoContainer() | |-ReactMount._renderNewRootComponent() | |-instantiateReactComponent() | |~batchedMountComponentIntoNode() upper half |~mountComponentIntoNode() (平台无关) |-ReactReconciler.mountComponent() | |-ReactCompositeComponent.mountComponent() | |-ReactCompositeComponent.performInitialMount() | |-instantiateReactComponent() _|_ |-ReactDOMComponent.mountComponent() lower half |-_mountImageIntoNode() (HTML DOM 相关) _|_
Wenn Sie sich den Quellcode ansehen, werden wir viel transaktionsbezogenen Code bemerken. Wir werden ihn ignorieren Dies wird vorerst im Artikel erläutert. Derzeit kann verstanden werden, dass es sich beim Aufruf von „transaktion.perform“ tatsächlich um einen Funktionsaufruf für den ersten Parameter handelt. Nachdem Sie einen Teil des Vorlagencodes übersprungen haben, übernimmt die mountComponentIntoNode-Methode tatsächlich die Arbeit.
// 文件位置:src/renderers/dom/client/ReactMount.js function mountComponentIntoNode( wrapperInstance, // ReactCompositeComponent[T] container, // document.getElementById("root") transaction, shouldReuseMarkup, context ) { ... var markup = ReactReconciler.mountComponent( wrapperInstance, transaction, null, ReactDOMContainerInfo(wrapperInstance, container), context, 0 /* parentDebugID */ ); ... ReactMount._mountImageIntoNode( markup, container, wrapperInstance, shouldReuseMarkup, transaction ); }
ReactReconciler.mountComponent wird zum Erstellen von DOM-Elementen verwendet ReactMount._mountImageIntoNode ist das neu erstellte DOM Das Element wird an die Seite angehängt. ReactReconciler.mountComponent ruft die mountComponent-Methode von ReactCompositeComponent[T] auf. Bevor Sie sich die mountComponent-Methode ansehen, müssen Sie zunächst hostContainerInfo vorbereiten, das von ReactDOMContainerInfo generiert wird:
// 文件位置:src/renderers/shared/stack/reconciler/ReactContainerInfo.js function ReactDOMContainerInfo( topLevelWrapper, // ReactCompositeComponent[T] node // document.getElementById("root") ) { var info = { _topLevelWrapper: topLevelWrapper, _idCounter: 1, _ownerDocument: node ? node.nodeType === DOC_NODE_TYPE ? node : node.ownerDocument : null, _node: node, _tag: node ? node.nodeName.toLowerCase() : null, _namespaceURI: node ? node.namespaceURI : null, }; ... return info; }
Jetzt ist die Beziehung zwischen den Instanzen wie folgt:
Sehen Sie sich weiterhin die mountComponent-Methode an:
// 文件位置:src/renderers/shared/stack/reconciler/ReactCompositeComponent.js mountComponent: function ( transaction, hostParent, hostContainerInfo, context ) { ... // this._currentElement 为ReactElement[2](TopLevelWrapper) var publicProps = this._currentElement.props; var publicContext = this._processContext(context); // TopLevelWrapper var Component = this._currentElement.type; ... // Initialize the public class var doConstruct = shouldConstruct(Component); // 生成TopLevelWrapper 实例 var inst = this._constructComponent( doConstruct, publicProps, publicContext, updateQueue ); ... var markup; ... markup = this.performInitialMount(renderedElement, hostParent, hostContainerInfo, transaction, context ... return markup; }, performInitialMount: function (renderedElement, hostParent, hostContainerInfo, transaction, context) { // TopLevelWrapper 实例 var inst = this._instance; ... // If not a stateless component, we now render if (renderedElement === undefined) { // 返回值为 ReactElement[1] renderedElement = this._renderValidatedComponent(); } // 返回 ReactNodeTypes.HOST var nodeType = ReactNodeTypes.getType(renderedElement); this._renderedNodeType = nodeType; // instantiateReactComponent.js var child = this._instantiateReactComponent( renderedElement, nodeType !== ReactNodeTypes.EMPTY /* shouldHaveDebugID */ ); this._renderedComponent = child; var markup = ReactReconciler.mountComponent( child, transaction, hostParent, hostContainerInfo, this._processChildContext(context), debugID ); ... return markup; },
Beim Ausführen von var child = this._instantiateReactComponent
wird die im vorherigen Artikel erwähnte instantiateReactComponent
-Datei aufgerufen:
// 文件位置:src/renderers/shared/stack/reconciler/instantiateReactComponent.js function instantiateReactComponent(node, shouldHaveDebugID) { var instance; ... } else if (typeof node === 'object') { ... // element.type 为 ‘h1’ if (typeof element.type === 'string') { instance = ReactHostComponent.createInternalComponent(element); } return instance; }
ReactDom wird beim Ausführen ausgeführt, um ReactDOMComponent in ReactHostComponent einzufügen.createInternalComponent ruft schließlich ReactDOMComponent auf: ReactDefaultInjection.inject()
// 文件位置:src/renderers/dom/shared/ReactDomComponent.js function ReactDOMComponent(element) { // h1 var tag = element.type; validateDangerousTag(tag); // ReactElement[1] this._currentElement = element; this._tag = tag.toLowerCase(); this._namespaceURI = null; this._renderedChildren = null; this._previousStyle = null; this._previousStyleCopy = null; this._hostNode = null; this._hostParent = null; this._rootNodeID = 0; this._domID = 0; this._hostContainerInfo = null; this._wrapperState = null; this._topLevelWrapper = null; this._flags = 0; }
Der bisherige Aufrufstapel:
|=ReactMount.render(nextElement, container, callback) ___ |=ReactMount._renderSubtreeIntoContainer() | |-ReactMount._renderNewRootComponent() | |-instantiateReactComponent() | |~batchedMountComponentIntoNode() upper half |~mountComponentIntoNode() (平台无关) |-ReactReconciler.mountComponent() | |-ReactCompositeComponent.mountComponent() | |-ReactCompositeComponent.performInitialMount() | |-instantiateReactComponent() _|_ |-ReactDOMComponent.mountComponent() lower half |-_mountImageIntoNode() (HTML DOM 相关下一篇讲解) _|_
Das obige ist der detaillierte Inhalt vonReact erste Rendering-Analyse 2 (reine DOM-Elemente). Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!