React 回忆录(三)使用 React 渲染界面
Hi 各位,欢迎来到 React 回忆录!? 在上一章中,我介绍了 React 框架的“五大特点”:虚拟DOM,组件化,声明式代码,单向数据流和纯粹的 JavaScript 语法。在本章中,我们将谈到 React 是如何渲染 UI 的,以及在这个过程中所表现出的 组件化 思想。
01. React 渲染界面的方式
在 React 等大型前端框架出现之前,我们渲染 UI 元素的方式是使用字符串模板。而在 React 中,我们通过使用JavaScript 对象来渲染 UI 元素。
在上一章我们提到过,React 为了节省频繁操作 DOM 所耗费的前端性能,提出了虚拟DOM的概念,在这里我们所创建的 JavaScript 对象即是用来描述“页面看起来是什么样子”的虚拟DOM节点。“虚拟DOM”是如何最终转化为“真实DOM“并展现在浏览器中的呢?这里面的复杂工作(操作 DOM 树,添加节点)由 React 完成。
让我们先看看如何通过一个 JavaScript 对象创建一个虚拟的DOM节点(即 React 元素):
// 为了创建一个 React 元素,我们需要使用 React.createElement API
const element = React.createElement('h1',{className: 'greeting'},'Hello, world!'
);
复制代码
该 API 最终会返回一个大致如下格式的 JavaScript 对象:
const element = {type: 'h1',props: {className: 'greeting',children: 'Hello, world'}
};
复制代码
React 会为这个 JavaScript 对象在生成的虚拟DOM树上找到一席之地,并最终和浏览器中的真实 DOM 树合并,渲染视图。
然而在实际开发中,你几乎不会使用到 React.createElement
API,而是像下方这样创建 React 元素:
const element = (<h1 className="greeting">Hello, world!</h1>
);
复制代码
这种创建方式是通过一种叫做 JSX
的 JavaScript 语法扩展实现的,而对于 JSX
的概念在这里我就不再进一步阐述了,你大可以将它理解为一种简洁,高效创建 React 元素的语法糖,用来更加优雅的构建整个应用的虚拟 DOM。
值得一提的是,JSX
并不是 React 框架的一部分(这源于 React 代码组织上尽量分而治之的哲学),因此 React 并不像负责合并虚拟DOM与真实DOM那样,负责将由 JSX 语法写成的代码转化为使用了 React.createElement
API 的 JavaScript 对象。
那谁来做这件事呢?答案是 Babel
。而通常,我们使用 webpack
来打包我们的 JavaScript代码并输送至 Babel
进行转译。现在你明白了,为什么 React
,webpack
和Babel
总是像连体婴儿一样出现在一起。
到目前为止,我们已经知道如何创建 React 元素了,但实际上我们只是“创建“而已,离元素被真正展现在浏览器上,还查了关键的一步”渲染“。
在这里我们加快脚步,想要将之前创建好的 React 元素渲染出来,我们需要使用如下代码:
<div id="root"></div>const element = <h1>Hello, world</h1>;// 使用 ReactDOM.render API
ReactDOM.render(element,document.getElementById('root')
);
复制代码
没错,id 为 root
的 DOM元素将会成为整个虚拟DOM树的根节点。至此,我们已经掌握了把 React 元素转换为虚拟DOM节点,再在浏览器上渲染出该元素的整个流程。然而,只是能够使用 React 渲染视觉元素还远远谈不上发挥了 React 的价值。别忘了 React 是作为大型前端框架存在的(虽然相较于其他大型前端框架,它的组件并不完备),React 的真正价值在于:使用 React 元素简洁,高效的实现各种复杂的业务逻辑。
如何做到这一点呢?答案是使用React 组件。
02. React 组件
React 组件不仅可以使我们有能力打包一堆视觉元素而且还可以使我们有能力打包一系列相对应的交互行为。可以说:React 组件是构成 React 应用的基石。
那什么是 React 组件呢?你可以想象 React 组件就像是一个工厂,它接收一些列被称为属性的物料,最终生产(返回)React 元素/组件。
让我们换个角度说,React 组件本质上就是一个 JavaScript 函数,它接收一系列参数,返回 React 元素/组件。让我们看看它是被如何书写的:
import React form 'react'
import ReactDOM form 'react-dom'function Button(props) {return <button>{props.buttonName}</button>
}
复制代码
看到了吗,React 组件完全符合之前我们提到过的组件化思想,接收参数,返回UI元素。
以组件化的角度思考构建 React 应用是一个非常棒的想法,因为组件化就意味着模块化与可重用性。组件类就像是一个工厂生产组件的实例,这些组件类完全符合”单一响应原则“与”DOT“原则。
在 React 的官方文档中,大量的 React API 是关于组件的。因此组件是 React 非常重要的一个概念,从本质上说,组件是 React 给予我们的主要的封装单元。通过一个个组件,我们能像搭积木一样快速搭起一个拥有复杂交互逻辑和视觉界面的大型应用,并且应用中的每个视觉单元又拥有着非常清晰的责任。
希望到这里你能体会到 React 在构建大型应用时的价值了,它使我们能够关注于应用中的一小部分,而不会无意中影响到应用的其余部分(即每个组件都符合了”高内聚,低耦合“的原则)。使用 React,我们更容易写出清晰,优雅的代码。
03. 小结
最后,让我们再次总结在 React 中使用组件渲染界面的两点优势:
- 易于重用:我们可以在任何时间地点调用一个组件;
- 方便定制:通过给予组件不同属性,我们可以获得不同的 UI 元素;
通过这一章的介绍,希望各位有所收获,如果有任何问题或建议,也欢迎各位在评论区内留言,下一章见 ?
PS:?如果你对该专题感兴趣,别忘了订阅本专栏,确保及时收到更新通知。记得点击下方?的各个按钮,让我知道你认可我的付出,这是激励我持续产出的动力和源泉 ?。
下个章节见 ? ? ?!
React 回忆录(三)使用 React 渲染界面相关推荐
- 传智播客 React 入门 三天课程
传智播客 React 入门 三天课程 第一天 理论和配置 虚拟DOM和DIFF算法 React 的核心是虚拟DOM和DIFF算法.DIFF 算法确保虚拟DOM高效运行(从上到下分别是 tree-dif ...
- 如何使用React提前三天计划
by Mohit Jain 由Mohit Jain 如何使用React提前三天计划 (How you can plan three days ahead with React) Today we'll ...
- React Native三端同构
React Native三端同构,即iOS.Android.Web共用一套代码,已知React Native已经支持iOS.Android,所以只需要做支持Web的工作就行了. 如何同构 我们可以利用 ...
- React Native 三端同构实战
WeiboGoogle+用电子邮件发送本页面 0 React Native 三端(Web.iOS.Android)同构是指在不改动原 React Native 的代码下,让其在浏览器中运行出和在 Re ...
- 为什么学习React Native三点原因
React Native不到两岁,兼容Android平台刚刚1年.我学习React Native其实也就不到1年,不算长,也不算短. Paul Graham在文章中写过:大多数人真正注意到你的时候,不 ...
- [react] 什么是浅层渲染?
[react] 什么是浅层渲染? 当为 React 写单元测试时,浅层渲染(Shallow Renderer) 会变得十分有用.浅层渲染使你可以渲染 "单层深度" 的组件,并且对组 ...
- [react] React怎样跳过重新渲染?
[react] React怎样跳过重新渲染? 生命周期 shouldComponentUpdate return false ? 个人简介 我是歌谣,欢迎和大家一起交流前后端知识.放弃很容易, 但坚持 ...
- [react] 如何提高组件的渲染效率呢?
[react] 如何提高组件的渲染效率呢? 类组件: 1.继承PureComponent 2.使用shouldComponentUpdate优化 函数组件: 1.memo模拟PureComponent ...
- [react] 怎样有条件地渲染组件?
[react] 怎样有条件地渲染组件? {condition && <Component />} or {condition ? <Component /> : ...
最新文章
- pip经常的使用技巧
- Java URL协议扩展实现
- 前端学习(2122):项目演示
- python 补前导零_Python正则表达式| 程序从IP地址中删除前导零
- OEA中的缓存模块设计
- python 代码片段24
- 15.导入网表及status介绍[原创]
- 分位数回归(quantile regression)R实现
- 武汉互联网公司和生活成本
- hadoop 8088端口网页无法打开的原因分析
- PHP Class - 图片水印
- C++面向对象程序设计:地铁自动售票系统
- Ubuntu8.04最全问题汇总
- 服务条款和隐私_数据中心设备和条款| 第1部分
- 什么是Portable Version?
- Python——文档
- 携手抗击疫情,雀巢大家庭在行动
- Android 点击图片放大至全屏 再次点击关闭过度动画 Shared Element效果(共享元素效果)
- latex 图片、表格、定义、理论 简单示例
- CentOS7的Tiger VNC设置