写在前面:很多前端自学者在完成了 HTML/CSS/JavaScript 三大语言的学习之后,往往容易(比如我)产生迷茫,不知道下一步该学什么,怎么学。
我想,在掌握扎实的语言基础后,相当有必要开始进行前端主流框架的学习。接下来我将把我自己的学习过程和学习指南做分享,希望多和掘金社区的朋友们交流。
第一个问题:什么是 React JSX?
w3cschools.com 给出的介绍是:
-
JSX stands for JavaScript XML.
-
JSX allows us to write HTML in React.
-
JSX makes it easier to write and add HTML in React.
JSX 的全称是:JavaScript XML
将 JavaScript XML 分别来看:
1. JavaScript :属于 HTML 和 Web 的编程语言,对网页行为进行编程,和定义网页内容的 HTML、定义网页格式的 CSS、一起被人熟知的定义网页动作的语言
2. XML: 可扩展标记语言(Extensible Markup Language),XML 可用来传输和存储数据,其焦点是数据的内容,是对 HTML 的补充而不是替代
个人理解:JSX 是一种允许在 JavaScript 中混合写入类似于 HTML 的语法规定,便于程序员使用 React 库进行网页开发,在很多常见的场景下,JSX 看起来像 HTML,行为也像 HTML。但是,它最终是被设计为翻译成 JavaScript
第二个问题:为什么是 React JSX?
从本质上看,JSX 仅仅只是 React.createElement(component, props, ...children)函数的语法糖。也就是说这种语法对语言的功能没有影响,但是更方便程序员使用。语法糖让程序更加简洁,有更高的可读性。
我们可以在 React 中使用 JSX 来替代常规的 JavaScript,JSX 的使用不是必须的,但是如果不使用 JSX 则会带来很大的不便。
React 认为渲染逻辑本质上与其他 UI 逻辑内在耦合,比如,在 UI 中需要绑定处理事件、在某些时刻状态发生变化时需要通知到 UI,以及需要在 UI 中展示准备好的数据。
React 并没有采用将标记与逻辑进行分离到不同文件这种人为地分离方式,而是通过将二者共同存放在称之为“组件”的松散耦合单元之中,来实现关注点分离。
React 不强制要求使用 JSX,但是大多数人发现,在 JavaScript 代码中将 JSX 和 UI 放在一起时,会在视觉上有辅助作用。它还可以使 React 显示更多有用的错误和警告消息。
JSX 有如下优点:
- 类 XML 语法容易接受,结构清晰
- 增强 JavaScript 语义
- 抽象程度高,屏蔽 DOM 操作,跨平台
- 代码模块化
为了要使用 JSX 语法,我们必须要引入 babel 的 JSX 解析器,把 JSX 转化成 JS 语法,这个工作会由 babel 自动完成。同时引入 babel 后,我们就可以使用新的 es6 语法,babel 会帮我们把 es6 语法转化成 es5 语法,兼容更多的浏览器。
第三个问题:怎么配置实践 React JSX 所需的环境(当然包括了其他 React 实践所需要的部分环境)?
-
安装 Node.js
进入 Node.js 官网选择适合自己操作系统的最新的版本下载,下载完成后在命令行中输入:
node -v如果得到版本号证明下载成功,当前最新版本 v12.16.1 -
安装 webpack
命令行中键入:
npm install webpack -g下载完成后在命令行中输入:
webpack -v如果得到版本号证明下载成功,当前最新版本 4.42.0 -
使用 webpack 初步建立一个项目
-
新建文件夹,使用
cd命令跳转至该文件目录下,运行npm init -y快速初始化项目 -
在该文件夹下新建 src 和 dist 文件夹,在 src 目录下创建 index.html 文件和 index.js 文件
-
返回上一层文件夹,新建 webpack.config.js 文件,并做配置如下:
module.exports = { mode:'development' } //此处没有进行打包入口文件的配置,因为在此版本下的 webpack 中默认的打包入口路径是 src->index.js
-
-
在 package.json 中增加 dev 配置:
"scripts": { "dev": "webpack-dev-server --open --port 3000 --hot --process --compress --host 127.0.0.1" }至此可以在该目录下使用命令行 `npm run dev `在的配置对应的端口上运行网页,如果各工具版本无冲突,配置正确,那么应该会显示如下内容:> webpack-base@1.0.0 dev C:\Users\Dongshufeng\webpack-base > webpack-dev-server --open --port 3000 --hot --process --compress --host 127.0.0.1 i 「wds」: Project is running at http://127.0.0.1:3000/ i 「wds」: webpack output is served from / i 「wds」: Content not from webpack is served from C:\Users\Dongshufeng\webpack-base i 「wdm」: wait until bundle finished: / i 「wdm」: Hash: 9d2c7c98d724d42724c0 Version: webpack 4.42.0 Time: 1681ms Built at: 2020-03-21 11:04:03 -
接下来要是启用 JSX 语法的配置
安装 babel 插件
运行
npm i babel-loader @babel/core @babel/plugin-transform-runtime @babel/runtime -D运行
npm i @babel/preset-env @babel/plugin-proposal-class-properties -D安装能够识别转换JSX语法的包,就是将JSX转化为JavaScript
@babel/preset-react运行
npm i @babel/preset-react -D添加 .babelrc 配置文件
{ "presets": ["@babel/preset-env", "@babel/preset-react"], "plugins": ["@babel/plugin-transform-runtime", "@babel/plugin-proposal-class-properties"] }添加babel-loader配置项:
module: { //要打包的第三方模块 rules: [{ test: /\.js|jsx$/, use: 'babel-loader', exclude: /node_modules/ }] }
至此我们成功地从零开始配置了可供 JSX 运行的环境。在此过程中:为提升 npm 的下载速度,可以尝试使用 cnpm 或设置淘宝镜像 npm config set registry https://registry.npm.taobao.org
一定要注意各环节版本上的差异,细心且耐心地进行下载和配置。
第四个问题:如何使用 JSX?
首先可以对比一下使用与不使用 JSX 的区别:
使用 JSX:
import React from 'react'
import ReactDOM from 'react-dom'
const mydiv =
<div id = "mydiv" title = "div aaa">
this is a div element
</div>
ReactDOM.render(mydiv,document.getElementById('app'))
不使用 JSX:
import React from 'react'
import ReactDOM from 'react-dom'
const mydiv =
React.createElement('div',{id :'mydiv',title : 'div aaa'},'this is a div element')
ReactDOM.render(mydiv,document.getElementById('app'))
运行后可以发现:JSX 的使用与否,表面上并不影响页面的呈现效果,但是二者的可读性和易用性是不可同日而语的
那么如何使用 JSX?
1. JSX 必须被严格闭合
在 HTML 中不严格的闭合可能不会造成严重后果(当然也应该闭合标签),但是在 JSX 中,不严格的闭合会引起编译器报错:
(property) JSX.IntrinsicElements.div: React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement>
JSX element 'div' has no corresponding closing
2. JSX 标签必须要有一个父级元素
也就是说,类似于 HTML DOM 树,必须有一个根节点,下面的这种用法是错误的,因为两个标签是并列的关系且没有父级元素:
const mydiv =
<div id = "mydiv" title = "div aaa">
this is a div element
</div>
<h1>this is a h1 tag</h1>
这种情况下会报错:
JSX expressions must have one parent element.ts(2657)
3. 遇到 HTML 标签(以 < 开头),就用 HTML 规则解析;遇到代码块(以 { 开头),就用 JavaScript 规则解析。以下是一些常见的使用方法
-
使用变量
import React from 'react' import ReactDOM from 'react-dom' const mydiv = <div id = "mydiv" > the number is: {3+3} </div> ReactDOM.render(mydiv,document.getElementById('app')) -
使用数组(这里的代码是没有问题的,但是找不到原因为何在 .md 文件中从
</h2>开始显示颜色异常)JSX 允许在模板中插入数组,数组会自动展开所有成员;
数组名[i]会选定数组中的第个i元素:import React from 'react' import ReactDOM from 'react-dom' var myarr = [ <h1>this is h1</h1>, <h1>this is h2</h2>, ]; ReactDOM.render(<div>{myarr[0]}</div>, document.getElementById('app')) -
JSX 的条件判断
JSX 中没有条件判断,可以使用三目运算符
import React from 'react' import ReactDOM from 'react-dom' var i = 1; ReactDOM.render( <div> <h1>{i == 1?'true':'flase'}</h1> </div>, document.getElementById('app') )
4.CSS的指定
不同于 HTML 的是,在 JSX 中,style 属性不能包含 CSS,而是引用一个包含样式信息的对象:
import React from 'react';
import ReactDOM from 'react-dom';
class MyHeader extends React.Component {
render() {
return (
<div>
<h1 style={{color: "red"}}>Hello Style!</h1>
<p>Add a little style!</p>
</div>
);
}
}
ReactDOM.render(<MyHeader />, document.getElementById('app'));