function instantiateComponent(element) { var type = element.type; if(typeof type === 'function') { return new CompositeComponent(type); }else if(typeof type === 'string') { return new DOMComponent(type); } }
getPublicInstance() { // For composite components, expose the class instance. return this.publicInstance; }
mount() { var element = this.currentElement; var type = element.type; var props = element.props;
var publicInstance; var renderedElement; if (isClass(type)) { // Component class publicInstance = new type(props); // Set the props publicInstance.props = props; // Call the lifecycle if necessary if (publicInstance.componentWillMount) { publicInstance.componentWillMount(); } renderedElement = publicInstance.render(); } else if (typeof type === 'function') { // Component function publicInstance = null; renderedElement = type(props); }
// Save the public instance this.publicInstance = publicInstance;
// Instantiate the child internal instance according to the element. // It would be a DOMComponent for <div /> or <p />, // and a CompositeComponent for <App /> or <Button />: var renderedComponent = instantiateComponent(renderedElement); this.renderedComponent = renderedComponent;
// Mount the rendered output return renderedComponent.mount(); } }
getPublicInstance() { // For DOM components, only expose the DOM node. return this.node; }
mount() { var element = this.currentElement; var type = element.type; var props = element.props; var children = props.children || []; if (!Array.isArray(children)) { children = [children]; }
// Create and save the node var node = document.createElement(type); this.node = node;
// Set the attributes Object.keys(props).forEach(propName => { if (propName !== 'children') { node.setAttribute(propName, props[propName]); } });
// Create and save the contained children. // Each of them can be a DOMComponent or a CompositeComponent, // depending on whether the element type is a string or a function. var renderedChildren = children.map(instantiateComponent); this.renderedChildren = renderedChildren;
// Collect DOM nodes they return on mount var childNodes = renderedChildren.map(child => child.mount()); childNodes.forEach(childNode => node.appendChild(childNode));
// Return the DOM node as mount result return node; } }