- jsx 不只是模板语法的一种,jsx 作为 react 框架的一大特色,与其运行机制有千丝万缕的联系
- jsx 是 JavaScript 的一种语法扩展工具,和模板语法很接近,但是充分具备 js 的能力
- 浏览器不会像对 js 一样直接支持,而是需要通过 Babel 转化
- Babel 是一种 JavaScript 编译工具,能够将 ES2015 以上的版本转化为向后兼容的 js 语法,适配低版本浏览器,另外还可以转化 jsx、typescript…
jsx 会被编译为 React.createElement()
, React.createElement()
将会返回一个 React Element
对象
1 2 3 4
| <div className="App"> <h1 className="app__title">Hello World</h1> <p className="app__desc">React and JSX</p> </div>
|
转换后
1 2 3 4 5 6 7 8 9 10
| "use strict";
React.createElement("div", { className: "App" }, React.createElement("h1", { className: "app__title" }, "Hello World"), React.createElement("p", { className: "app__desc" }, "React and JSX"));
|
createElement()
React.createElement()
接收 3 个以上参数:
- type: 要创建的 React 元素类型;可以是
标签字符串
如 “div”、”p”…;也可以是 React 组件
类型(class组件或者函数组件);或者是React fragment类型
- config: 写在标签上的
属性的集合
,js对象
格式,若标签上未添加任何属性则为 null
- chidlren:
第三个及以后
的参数为当前 React 节点的子节点
;若是文本节点
则为字符串类型;否则为新的 React.createElement
创建的元素
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40
| export function createElement (type, config, children) { let propName; const props = {}
for (propName in config) { if ( hasOwnProperty.call(config, propName) && !RESERVED_PROPS.hasOwnProperty(propName) ) { props[propName] = config[propName]; } } const childrenLength = arguments.length - 2; if (childrenLength === 1) { props.children = children; } else if (childrenLength > 1) { const childArray = Array(childrenLength); for (let i = 0; i < childrenLength; i++) { childArray[i] = arguments[i + 2]; } props.children = childArray; }
return ReactElement( type, key, ref, self, source, ReactCurrentOwner.current, props, ); }
|
ReactElement()
React.createElement()
主要用于数据的格式化,形成 ReactElement()
所预期的格式并传入 ReactElement()
,后者将 组装完成的 react element 对象返回
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
| const ReactElement = function(type, key, ref, self, source, owner, props) { const element = { $$typeof: REACT_ELEMENT_TYPE, type: type, key: key, ref: ref, props: props, _owner: owner, } if (__DEV__) { } return element; }
|
对比
1 2 3 4 5 6 7
| console.dir(React.createElement( 'h1', { id: 'HelloComponent' }, 'Hello World !' ));
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
| { $$typeof: Symbol(react.element), type: "h1", key: null, ref: null, props: { id: "HelloComponent", children: "Hello World !", __proto__: Object, _owner: null, }, _store: { validated: false, __proto__: Object, }, _self: null, _source: null, __proto__: Object }
|
ReactDOM.render()
ReactDOM.render(<App />, document.getElementById('root'))
1 2 3 4 5 6 7 8
| ReactDOM.render( element, container, callback? )
|