前端小白学 React 框架(三)
JSX
认识JSX
下面是一个简单的JSX代码:
// 1.定义根组件
const element = <div>He1lo World</div>;
// 2.渲染根组件
const root = ReactDOM.createRoot(document.querySelector("#root"));
root.render(element);
什么是JSX
JSX是一种JavaScript语法扩展(extension),也在很多地方称之为JavaScript XML,因为看起就是一段XML语法,它用于描述我们的UI界面,并且其完成可以和JavaScript融合在一起使用,它不同于Vue中的模块语法,你不需要专门学习模块语法中的一些指令(比如v-for、v-if、v-else、v-bind)
为什么React选择了JSX
React认为渲染逻辑本质上与其他UI逻辑存在内在耦合:
- 比如UI需要绑定事件(button、a原生等等)
- 比如UI中需要展示数据状态
- 比如在某些状态发生改变时,又需要改变UI
HTML
和JS
之间是密不可分,所以React没有将标记分离到不同的文件中,而是将它们组合到了一起,这个地方就是组件(Component)
JSX的书写规范
- JSX的顶层只能有一个根元素,所以我们很多时候会在外层包裹一个div元素(或者使用后面我们学习的Fragment)
- 为了方便阅读,我们通常在jsx的外层包裹一个小括号
()
,这样可以方便阅读,并且jsx可以换行书写 - JSX中的标签可以是单标签,也可以是双标签,如果是单标签,必须以
/>
结尾
JSX基本语法
JSX注释
没啥好说的,直接上代码:
<div>
{/* 这个是JSX的注释 */}
<h2>{message}</h2>
</div>
JSX插入内容
JSX嵌入变量作为子元素
- 当变量是Number、String、Array类型时,可以直接显示
- 当变量是null、undefined、Boolean类型时,内容为空
- 如果希望可以显示null、undefined、Boolean,那么需要转成字符串
- 转换的方式有很多,比如toString方法、和空字符串拼接,String(变量)等方式
- Object对象类型不能作为子元素(not valid as a React child)
这里的子元素,就相当于标签的内容,如果是作为标签属性的值那又会有不同
下面是一个测试案例:
class App extends React.Component {
constructor() {
super();
this.state = {
message: 'Hello World',
num: 1,
list: ['a', 'b', 'c'],
a: undefined,
b: null,
c: true,
d: {}
}
}
render() {
const { message, num, list, a, b, c }=this.state;
return (
<div>
<h2>{message}</h2>
<h2>{num}</h2>
<h2>{list}</h2>
<h2>{a}</h2>
<h2>{b}</h2>
<h2>{c}</h2>
</div>
)
}
}
在页面上会显示如下结果:
可以发现显示的结果如上面的规则描述的一样,那么如果显示一个对象呢?下面演示一下,代码就不展示了,很简单,大家自己加一下就可以了,直接放上效果图吧:
和预期的一样,果然报错了 🤪
插入表达式
- 可以插入表达式
- 可以插入三元运算符
- 可以调用函数获得结果
然后上代码,看一看效果吧:
class App extends React.Component {
constructor() {
super();
this.state = {
firstName: 'Karl',
lastName: 'fang',
age: 23,
hobby: ['吃', '喝', '玩', '乐']
}
}
render() {
const { firstName, lastName, age, hobby }=this.state;
const fullName = firstName + " " + lastName;
return (
<div>
{/* 可以插入表达式 */}
<h2>{10 + 20}</h2>
<h2>{firstName + " " + lastName}</h2>
<h2>{fullName}</h2>
{/* 可以插入三元运算符 */}
<h2>{age > 18 ? '成年人' : '未成年人'}</h2>
{/* 可以调用函数获得结果 */}
<ul>{hobby.map(item => <li>{item}</li>)}</ul>
</div>
)
}
}
页面效果如下:
JSX绑定属性
基本属性绑定
- 比如元素都会有title属性
- 比如img元素会有src属性
- 比如a元素会有href属性
- 比如元素可能需要绑定class
- 比如原生使用内联样式style
案例代码如下:
class App extends React.Component {
constructor() {
super();
this.state = {
title: '我是h2',
src: 'https://d302.paixin.com/thumbs/33336542/351710674/staff_1024.jpg?imageView2/2/w/500/h/360/format/webp/interlace/1/q/90/ignore-error/1',
href: 'https://www.baidu.com',
}
}
render() {
const { title, src, href }=this.state;
return (
<div>
{/* 基本绑定 */}
<h2 title={title}>H2标题</h2>
<img src={src} />
<br />
<a href={href}>百度一下</a>
</div>
)
}
}
然后查看一下页面的效果:
class属性绑定
来下一个简单的页面代码吧:
class App extends React.Component {
constructor() {
super();
this.state = {
message: 'Hello World'
}
}
render() {
const { message }=this.state;
return (
<div>
{/* 绑定class属性 */}
<h2 class="item">{message}</h2>
</div>
)
}
}
以下是运行的结果:
虽然说页面能正常显示,但是能看到报了warning
,这是因为我们写的是JSX语法,也就是说我们写的是js,那么在js中class
是关键字,但是babel也能给我们正常的解析出来,但是为了避免引起误会,官方推荐使用className
这个属性来绑定class
属性,因此只要把上述代码的class
改为className
即可。
如果想动态绑定属性,也和基本属性一样用{}
进行绑定,绑定是字符串即可。
style属性绑定
⭕️ style
属性有点特殊,它必须用对象形式来绑定,也就是在{}
内再写一个对象,但是之前不是说{}
不能绑定对象嘛?那是因为绑定数据的时候是最为子元素内部的值来绑定的,那个时候确实不能,但是这里是作为style
属性的话就可以了,就和Vue中绑定style
是一样的。
render() {
const { message, classList }=this.state;
return (
<div>
{/* 绑定class属性 */}
<h2 className={classList.join(' ')}>{message}</h2>
{/* 绑定style属性: 绑定对象类型 */}
<p style={{color: 'red'}}>red text</p>
</div>
)
}
因为在React中编写CSS样式的方法非常多,后面会写。
效果如下:
写在最后
如果大家喜欢的话可以收藏本专栏,之后会慢慢更新,然后大家觉得不错可以点个赞或收藏一下 🌟。
本节的源码放在作者的GitHub仓库里,分别是:
转载自:https://juejin.cn/post/7232665460713046075