一、JSX来历
React认为一切基于组件,组件自然而然要和模板联系在一起,把逻辑和模板分开放置是一种笨重的思路。所以,React创造了一种名为JSX的语法格式来架起一道它们之间的桥梁。
- 注意:
- < script > 标签的 type 属性为 text/babel,这是React 独有的 JSX 语法,跟 JavaScript 不兼容。凡是在页面中直接使用 JSX 的地方,都要加上 type=“text/babel”。
- 一共用了三个库: react.js 、react-dom.js 和 browser.min.js ,它们必须首先加载。其中,react.js 是 React 的核心库,react-dom.js 是提供与 DOM 相关的功能, browser.min.js的作用是将 JSX 语法转为 JavaScript 语法。
- 特点:
- 类XML语法容易接受,结构清晰
- 增强JS语义
- 抽象程度高,屏蔽DOM操作,跨平台
- 代码模块化
二、语法
JSX本身就和XML语法类似,可以定义属性以及子元素。唯一特殊的是可以用大括号来加入JavaScript表达式。
JSX基本语法规则:
- 遇到 HTML 标签(以 < 开头),就用 HTML 规则解析;
- 遇到代码块(以 { 开头),就用 JavaScript 规则解析。
1.JSX不是必须的
JSX编译器把2类似于HTML的写法转换成原生的JavaScript方法,并且会将传入的属性装换为对应的对象。它就类似于一种语法糖,把标签类型的写法转换成ReactElement提供的用来创建ReactElement的方法。
2.HTML标签与React组件
- React可以直接渲染HTML类型的标签,也可以渲染React的组件。
- React组件标签第一个字母用大写表示。JSX语法使用第一个字母大小写来区分是一个普通的HTML标签,还是一个React组件。
import React from 'react'
class Hello extends React.component{
...
// 直接return JSX语法
return <h1>Hello World!</h1>
}
let hello=<Hello />
// 等价于
let hello =React.creatElement(Hello);
3.JSX书写方式
- JSX 中的注释方式
{/*JSX 中的注释方式*/}
- jsx语法中只能有一个顶级标签(元素),如下写法是错误的,这和react的diff算法相关
ReactDOM.render(
<div>
</div>
<p></p>,
document.getElementById('root')
)
- JSX中所有的标签都必须有闭标签
ReactDOM.render(
<div>
<input type="text" />
<img src="" />
</div>,
document.getElementById('root')
)
- JSX本身是JS语法,所以一些JS中的保留字要用其他方式书写。eg.class=>className;
html标签的for属性(如:< label for=“msg” ></ label >)在jsx中变为< label htmlFor=“msg” ></ label >,
import React from 'react'
// 当一个标签里面为空时,可以使用自闭合
let divElement=<div className="foo" />;
// 等价于
let divElement=React.creatElement('div',{className:'foo'});
- 自定义属性:要加 data- 前缀
如果往原生 HTML 元素里传入 HTML 规范里不存在的属性,React 不会显示它们。如果需要使用自定义属性,要加 data- 前缀。
<div data-custom-attribute="foo" />
- 在JSX中我们通常是通过 {} 的方式插入值,但是设置style属性需要{{ }},
并且遇到-分割的属性时,使用小驼峰的写法,如:text-align —> textAlign
ReactDOM.render(
<div style={{background:red;}}>
{ 1+2 }
<div style={{ padding: 30, textAlign: 'center' }}>
</div>
</div>,
document.getElementById('root')
)
- 调用.css 文件中的css属性
... ...
import classes form './myCss.css'
ReactDOM.render(
<div className={classes['mycss']}>
</div>,
document.getElementById('root')
)
- 事件必须修正this指针,且绑定事件名时要使用小驼峰的写法
constructor{
**this.fun = this.fun.bind(this)**
}
//或
onClick = {() => ()} //绑定的事件名小驼峰写法
**onClick = {this.fun.bind(this)}**
- 求值表达式
在编写JSX时,在 { } 中不能使用语句(if语句、for语句等等),但可以使用求值表达式,这本身与JSX没有多大关系,是JS中的特性,它是会返回值的表达式。我们不能直接使用语句,但可以把语句包裹在函数求值表达式中运用。 - 条件判断的写法
在JSX中无法使用 if-else 语句,因为 JSX 只是函数调用和对象创建的语法糖。在 { } 中使用,是不合法的JS代码,不过可以采用三元操作表达式。
var HelloMessage = React.createClass({
render: function() {
return <div>Hello {this.props.name ? this.props.name : "World"}</div>;
}
});
ReactDOM.render(<HelloMessage name="xiaowang" />, document.body);
可以使用比较运算符(“||”) 来书写,如果左边的值为真,则直接返回左边的值,否则返回右边的值,与if的效果相同。
var HelloMessage = React.createClass({
render: function() {
return <div>Hello {this.props.name || "World"}</div>;
}
});
- 函数表达
( )有强制运算的作用。
var HelloMessage = React.createClass({
render: function() {
return <div>Hello {
//函数来了,注意看看看看看!!!
(function(obj){
if(obj.props.name)
return obj.props.name
else
return "World"
}(this))
}</div>;
}
});
ReactDOM.render(<HelloMessage name="xiaowang" />, document.body);
外括号“ )”放在外面和里面都可以执行。
唯一的区别是括号放里面执行完毕拿到的是函数的引用,然后再调用“function(){}(this)()”;
括号放在外面的时候拿到的是函数返回值。