React入门笔记(一) — 深入理解JSX
2017-06-19 16:13
621 查看
《一》、理解JSX |
JSX即
Javascrpt XML— — 一种在
React组件内部构建标签的类
XML语法。
JSX并不是新语言,也没有改变
JavaScript的语法,只是一种基于
ECMAScript的新特性,一种定义带属性树结构(
DOM结构)的语法
react可以不使用
JSX来编写组件,但是使用
JSX可以让代码可读性更高、语义更清晰、对
React元素进行抽象等等。
一、使用JSX好处
1、允许使用熟悉的语法来定义HTML元素树 2、提供了更加语义化且易懂的标签 3、程序结构更容易被直观化 4、抽象了
React Element的创建过程
5、可以随时掌控HTML标签以及生成这些标签的代码 63、是原生
javascript
使用JSX和不使用JSX的代码对比如下:
//开闭标签,在构建复杂的树形结构时,比函数调用和对象字面量更易读 //#使用JSX <div className="red">Children Text</div>; <MyCounter count={3 + 5} />; // 此处给一个js对象设置"scores"属性 var gameScores = { player1: 2, player2: 5 }; <DashboardUnit data-index="2"> <h1>Scores</h1> <Scoreboard className="results" scores={gameScores} /> </DashboardUnit>; //#不使用JSX React.createElement("div", { className: "red" }, "Children Text"); React.createElement(MyCounter, { count: 3 + 5 }); React.createElement( DashboardUnit, { "data-index": "2" }, React.createElement("h1", null, "Scores"), React.createElement(Scoreboard, { className: "results", scores: gameScores }) );1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
二、JSX 语法
【注意】 JSX代码需经babel 编译成javscript,目前主流浏览器才能正常识别,即在head中需添加:
<script src="https://cdnjs.cloudflare.com/ajax/libs/babel-core/5.8.24/browser.min.js"></script>1
1
React还需依赖的另外2个文件:react.js 是 React 的核心库,react-dom.js 是提供与 DOM 相关的功能,
并将
JSX代码放在
<script type='text/babel'>…
</script>中编写
<!DOCTYPE html> <html> <head> <meta charset="UTF-8" /> <title>Hello React!</title> <script src="build/react.js"></script> <script src="build/react-dom.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/babel-core/5.8.24/browser.min.js"></script> </head> <body> <div id="example"></div> <script type="text/babel"> ReactDOM.render( <h1>Hello, world!</h1>, document.getElementById('example') ); </script> </body> </html>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
【推广】上面必需核心库找不到的话,可以上本人github下载:https://github.com/mqy1023/react-basejs
JSX是
HTML和
JavaScript混写的语法,当遇到<
JSX就当
HTML解析,遇到 { 就当
JavaScript解析。
var names = ['Alice', 'Emily', 'Kate']; ReactDOM.render( <div> { names.map(function (name) { return <div>Hello, {name}!</div> }) } </div>, document.getElementById('example') );1
2
3
4
5
6
7
8
9
10
11
1
2
3
4
5
6
7
8
9
10
11
理解Array.prototype.map,返回一个新的数组
var friends = ['Jake Lingwall', 'Murphy Randall', 'Merrick Christensen']; var listItems = friends.map(function(friend){ return "<li> " + friend + "</li>"; }); console.log(listItems); // ["<li> Jake Lingwall</li>", "<li> Murphy Randall</li>", "<li> Merrick Christensen</li>"];1
2
3
4
5
1
2
3
4
5
JSX允许直接在模板插入
JavaScript变量。如果这个变量是一个数组,则会展开这个数组的所有成员
// arr变量是一个数组,结果 JSX 会把它的所有成员,添加到模板 var arr = [ <h1>Hello world!</h1>, <h2>React is awesome</h2>, ]; ReactDOM.render( <div>{arr}</div>, document.getElementById('example') );1
2
3
4
5
6
7
8
9
1
2
3
4
5
6
7
8
9
在React中,一个组件的HTML标签与生成这些标签的代码内在地紧密联系在一起。这意味和我们可以轻松地利用
Javascript强大魔力
1、使用三目运算符
render: function() { return <div className={this.state.isComplete ? 'is-complete' : ''}>...</div>; }1
2
3
1
2
3
2、使用变量/函数
getIsComplete: function() { return this.state.isComplete ? 'is-complete' : ''; }, render: function() { var isComplete = this.getIsComplete(); return <div className={isComplete}>...</div>; //或者直接返回函数 return <div className={this.getIsComplete()}>...</div>; }1
2
3
4
5
6
7
8
9
10
1
2
3
4
5
6
7
8
9
10
3、使用逻辑与(&&)或者逻辑或( || )运算符
由于对于null或false值React不会输出任何内容,因此可以使用一个后面跟随了期望字符串的布尔值来实现条件判断。如果这个布尔值为true,后续字符串会被使用
render: function() { return <div className={this.state.isComplete && 'is-complete'}>...</div>; }1
2
3
1
2
3
逻辑或,this.props.name为空时,className值等于is-complete
render: function() { return <div className={this.props.name || 'is-complete'}>...</div>; }1
2
3
1
2
3
4、函数调用
var HelloWorld = React.createClass({ render: function () { return <p>Hello, {(function (obj) { return obj.props.name ? obj.props.name : "World"; })(this)}</p> } });1
2
3
4
5
6
7
1
2
3
4
5
6
7
三、创建并渲染组件
//1、React.createClass 是用来创建一个组件 var HelloMessage = React.createClass({ render: function() { return <h1>Hello {this.props.name}</h1>; } }); //2、ReactDOM.render渲染组件 ReactDOM.render( <HelloMessage name="John" />, document.getElementById('example') );1
2
3
4
5
6
7
8
9
10
11
1
2
3
4
5
6
7
8
9
10
11
《二》、JSX和HTML不同点 |
一、渲染HTML标签和React组件
React.render方法可以渲染
HTML结构,也可以渲染
React组件。
1、渲染
HTML标签,声明变量采用首字母小写
var myDivElement = <div className="foo" />; ReactDOM.render(myDivElement, document.body);1
2
1
2
2、渲染
React组件,声明变量采用首字母大写
var MyComponent = React.createClass({/*...*/}); var myElement = <MyComponent someProperty={true} />; ReactDOM.render(myElement, document.body);1
2
3
1
2
3
二、非DOM属性
1、键(key)
key是一个可选的唯一标识符,当两个已经在于
DOM中的组件交换位置时,
React能够匹配对应的
key并进行相应的移动,且不需要完全重新渲染
DOM,提供渲染性能
2、引用(
ref)
ref允许父组件在
render方法之外保持对子组件的一个引用。在
JSX中,你可以通过属性中设置期望的引用名来定义一个引用。
render: function() { return <div> <input ref="myInput" ...> </input> </div> ); }1
2
3
4
5
6
1
2
3
4
5
6
然后你可以在组件的任何地方使用
this.refs.myInput获取这个引用了。通过引用获取到的这个对象被称为支持实例。它并不是真的
DOM,而是React在需要时用来创建
DOM的一个描述对象。你可以使用
this.refs.myInput.getDOMNode()访问真实的
DOM节点。
3、设置原始的
HTML
比如我们有一些内容是用户输入的富文本,希望展示相应的样式
var content='<strong>content</strong>'; ReactDOM.render( <div>{content}</div>, document.body );1
2
3
4
5
1
2
3
4
5
结果页面直接输出内容了:
React默认会进行
HTML的转义,避免
XSS攻击,如果要不转义,可以这么写:
ReactDOM.render( <div dangerouslySetInnerHTML={{__html: "<strong>content</strong>"}}></div>, document.body );1
2
3
4
1
2
3
4
三、事件
在所有的浏览器中,事件名已经被规范化并统一用onXXX驼峰形式表示var BannerAd = React.createClass({ handleClick: function(event) { //... }, render: function() { return <div onClick={this.handleClick}>Click Me!</div>; } })1
2
3
4
5
6
7
8
1
2
3
4
5
6
7
8
【注意】 React自动绑定了组件所有方法的作用域,因此你不需要手动绑定
handleClick: function(event) {...}, render: function() { //反模式 ————在React中手动给组件实例绑定 //函数作用域是没有必要的 return <div onClick={this.handleClick.bind(this)}>...</div>; }1
2
3
4
5
6
1
2
3
4
5
6
四、特殊属性
由于JSX会转换为原生的Javascript函数,因此有一些关键词我们是不能用的——如class和
for,对应JSX中属性写成
className和
htmlFor
//#使用JSX ReactDOM.render( <label className="xxx" htmlFor="input">content</label>, document.getElementById('example') ); //#不使用JSX ReactDOM.render( React.createElement('label', {className: 'xxx', htmlFor: 'input'}, 'content'), document.getElementById('example') );1
2
3
4
5
6
7
8
9
10
1
2
3
4
5
6
7
8
9
10
五、style样式
React把所有的内联样式都规范化为驼峰形式,与
Javascript中
DOM的
sytle属性一致。第一重大括号表示这是
JavaScript 语法,第二重大括号表示样式对象。
React.render( <div style={{color:'red'}}> xxxxx </div>, document.body ); //////////////////////////// var style = { color:'red', borderColor: '#999' } ReactDOM.render(<div style={style}>xxxxx</div>, document.body);1
2
3
4
5
6
7
8
9
10
11
12
1
2
3
4
5
6
7
8
9
10
11
12
六、注释
JSX本质就是
Javascript,因此你可以在标签内添加原生的
javascript注释。
注释两种形式
当作一个元素的子节点
内联在元素的属性中
var content = ( <Nav> {/* 一般注释, 用 {} 包围 */} <Person /* 多 行 注释 */ name={window.isLoggedIn ? window.name : ''} // 行尾注释 /> </Nav> );1
2
3
4
5
6
7
8
9
10
11
1
2
3
4
5
6
7
8
9
10
11
《三》、JSX延伸属性 |
一、不要改变props
如果提前就知道了组件的属性的话,写起来很容易。例如component组件有两个动态的属性foo和bar:
var component = <Component foo={x} bar={y} />;1
1
而实际上,有些属性可能是后续添加的,我们没办法一开始就确定,我们可能会写出下面不好的代码:
var component = <Component />; component.props.foo = x; // bad component.props.bar = y; // also bad1
2
3
1
2
3
这样写是错误的,因为我们手动直接添加的属性
React后续没办法检查到属性类型错误,也就是说,当我们手动添加的属性发生类型错误时,在控制台是看不到错误信息的。
在
React的设定中,初始化完
props后,
props是不可变的。改变
props会引起无法想象的后果。
二、延伸属性
为了解决这个问题,React引入了属性延伸
var props = {}; props.foo = x; props.bar = y; var component = <Component {...props} />;1
2
3
4
1
2
3
4
当需要拓展我们的属性的时候,定义个一个属性对象,并通过
{...props}的方式引入,
React会帮我们拷贝到组件的
props属性中。重要的是—这个过程是由
React操控的,不是手动添赋值的属性。
需要覆盖的时候可以这样写:
var props = { foo: 'default' }; var component = <Component {...props} foo={'override'} />; console.log(component.props.foo); // 'override'1
2
3
1
2
3
《四》、JSX 陷阱 |
一、自定义HTML属性
如果往原生 HTML元素里传入
HTML规范里不存在的属性,
React不会显示它们。
ReactDOM.render( <div dd='xxx'>content</div>, document.body );1
2
3
4
1
2
3
4
如果需要使用自定义属性,要加 data- 前缀。
ReactDOM.render( <div data-dd='xxx' aria-dd='xxx'>content</div>, document.body );1
2
3
4
1
2
3
4
二、组件render渲染函数中return注意点
如果return和JSX语句开头在同一行时,不需要括号;否则要括号包裹
//正确写法1 var HelloMessage = React.createClass({ render: function() { return <h1> Hello {this.props.name}</h1>; } }); //正确写法2 render: function() { return <h1>Hello {this.props.name}</h1>; } //正确写法3 render: function() { return ( <h1>Hello {this.props.name}</h1>); } //错误写法 render: function() { return <h1>Hello {this.props.name}</h1>; }1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
相关文章推荐
- React入门笔记(一) — 深入理解JSX
- 20150906 深入理解JVM之入门笔记
- React入门以及JSX语法理解
- 深入理解机器学习:从原理到算法 学习笔记-第1周 02简易入门
- React高级教程(es6)——(1)JSX语法深入理解
- React Native入门学习笔记三(JSX语法)
- 读 - 深入理解java虚拟机 - 笔记(七-1) - Java内存区域(2章)-对象创建
- 【Java学习笔记之二十六】深入理解Java匿名内部类
- 学习笔记之一:深入理解Activity的生命周期
- 深入理解JVM阅读笔记-对象引用
- 深入理解计算机系统-笔记1
- 2.[深入理解JVM笔记]Java内存模型与线程
- 深入理解Linux网络内幕学习笔记
- 深入理解Java:注解(Annotation)自定义注解入门
- 【转】深入理解Linux内核--信号(阅读笔记)
- 笔记:深入理解JVM 第5章 调优案例分析与实战
- 《深入理解Android(卷1)》笔记 1.第二章 深入理解JNI
- 深刻理解 React (一) ——JSX和虚拟DOM
- 读 - 深入理解java虚拟机 - 笔记(四) - java内存模型与线程(12章)-java内存模型和规则(简单解释)
- javascript笔记:通过对作用域链和执行环境的深入理解所得出的提高javascript代码性能的建议