JSX入门

JSX介绍

JSX(JavaScript XML)是一种 React 语法扩展,它允许你在 JavaScript 代码中编写类似 HTML 的结构。正如在 index.js 文件中看到的那样。

jsx 复制代码
const root = ReactDOM.createRoot(document.getElementById('root'));
root.render(
  <React.StrictMode>
    <App />
  </React.StrictMode>
);

本质上它只是 JavaScript 的一种语法糖(适用于 React 框架的 DSL,它专门用于描述 UI 结构。JSX 让 React 组件的编写更直观),最终会被编译成普通的 JavaScript 代码。

JSX特点

HTML + JavaScript混写

正如上面的示例代码,我们既可以使用类属于 HTML 标签的写法,也可以使用JavaScript表达式。

必须使用 className 代替 class

在 JSX 中,标签的 class 属性需要写成 className,因为 class 是 JavaScript 的关键字。

标签必须闭合

JSX 要求所有标签都必须正确关闭。

使用 camelCase 语法表示 HTML 属性

在 JSX 中,HTML 属性需要写成 camelCase 语法,比如 tabIndex 需要写成 tabIndex, onclick 变为 onClick。

JSX转译

浏览器不能直接理解 JSX,需要转译为 JavaScript 代码。通常使用 Babel 进行转译(Babel 是 React 最常用的 JSX 转译器,但也可以用 ESBuild、SWC、TypeScript 编译器来转译 JSX)。

JSX语法

在 JSX 中可以通过 {} 表达式来嵌入 JavaScript 表达式,但是你不能嵌入 JavaScript 语句,例如:

jsx 复制代码
const name = 'John';
const age = 30;
<div>
  <h1>Hello, {name}!</h1>
  <p>Your age is {age}.</p>
  <p>Your birthday is {new Date().toLocaleDateString()}.</p>
  <p>Your lucky number is {Math.random()}.</p>
  <p>Your lucky number is {Math.random() > 0.5 ? 'Lucky' : 'Unlucky'}.</p>
</div>

很多模板引擎都支持类似语法,比如 Vue、Angular、Nuxt 等。

JSX 实现列表渲染

在 JSX 中,可以使用 map 方法来渲染列表。例如:

jsx 复制代码
const names = ['Alice', 'Bob', 'Charlie'];
<div>
  <ul>
    {names.map((name, index) => (
        <li key={index}>{name}</li>
    ))}
    </ul>
</div>

在上面的示例中,我们使用了 map 方法来遍历 names 数组,并返回一个 li 元素。每个 li 元素的 key 属性被设置为当前元素的索引,这是 React 的推荐做法,因为 React 使用 key 来确定元素在列表中的位置,如果 key 值不变,React 会保留该元素的状态。状态是 React 的核心概念,它允许 React 组件在用户交互时保持状态,并自动更新 UI。后面我们会详细介绍 React 的状态管理。

JSX 实现条件渲染

前面说过 JSX 中只可以使用 Javascript 表达式,不能使用 Javascript 语句,所以不能使用 if else 语句,但是可以通过三元表达式,逻辑运算符,以及将if else 语句封装为函数等来实现条件渲染。例如:

jsx 复制代码
const isLoggedIn = true;
<div>
    {isLoggedIn ? (
        <p>Welcome, user!</p>
    ): (
        <p>Please log in.</p>
    )}
</div>

在上面的示例中,我们使用了三元表达式来判断用户是否登录,如果登录了,则显示欢迎信息,否则显示登录信息。还可以使用 && 运算符来实现条件渲染,例如:

jsx 复制代码
const isLoggedIn = true;
<div>
    {isLoggedIn && <p>Welcome, user!</p>}
    {!isLoggedIn && <p>Please log in.</p>}
</div>

逻辑与实现的初看有点不太好理解,一个常量怎么能和一个标签进行逻辑运算呢?而这正是 JSX 的魅力,它能够让我们在书写 UI 的时候同时混用 HTML 和 JavaScript。理解了这一点之后,就会发现上面的逻辑与的写法是很自然地。最后,我们来通过封装一个函数来实现条件渲染,例如:

jsx 复制代码
const names = ['Alice', 'Bob', 'Charlie', 'David'];
function selectTemplate(index = 0) {
  if (index === 0)
    return `Good morning, ${names[0]}!`;
  else if (index === 1)
    return `Good afternoon, ${names[1]}!`;
  else if (index === 2)
    return `Good evening, ${names[2]}!`;
  else
    return `Hello, ${names[3]}!`;
}
<div>
    <p>{selectTemplate(0)}</p>
</div>

在上面的示例中,我们封装了一个函数 selectTemplate,根据传入的 index 参数来选择不同的模板,并返回相应的字符串。然后,在 JSX 中,我们调用了该函数,并将返回值作为子元素。这样,我们就实现了条件渲染。

JSX 事件绑定

前面我们说过,JSX 中的事件绑定需要写成 onClick={handleClick} 的形式,其中 onClick 是事件名,handleClick 是事件处理函数。在 JSX 中,事件处理函数可以写成箭头函数,也可以写成普通函数,例如:

  1. 基础事件绑定

    jsx 复制代码
    function handleClick() {
        console.log('Clicked!');
    }
    <div>
        <button onClick={handleClick}>Click me</button>
    </div>

    在上面的示例中,我们定义了一个函数 handleClick,并在 JSX 中将其绑定到 button 元素的 onClick 事件上。当用户点击按钮时,该函数会被调用,并输出 "Clicked!" 到控制台。

  2. 捕获事件对象

    如果我们需要捕获事件对象,我们可以使用箭头函数,例如:

    jsx 复制代码
    function handleClick(event) {
        console.log('Clicked!');
        console.log(event.target.tagName);
    }
    <div>
        <button onClick={(event) => handleClick(event)}>Click me</button>
    </div>

    在上面的示例中,我们使用了箭头函数来定义事件处理函数,并在 JSX 中将其绑定到 button 元素的 onClick 事件上。当用户点击按钮时,该函数会被调用,并输出 "Clicked!" 到控制台,同时输出事件对象的 target 标签名。

  3. 同时捕获事件对象和参数

    如果我们需要同时捕获事件对象和参数,我们可以使用箭头函数,例如:

    jsx 复制代码
    function handleClick(event, name) {
        console.log('Clicked!');
        console.log(event.target.tagName);
        console.log(name);
    }
    <div>
        <button onClick={(event) => handleClick(event, 'John')}>Click me</button>
    </div>

    上面的示例中,我们使用了箭头函数来定义事件处理函数,并在 JSX 中将其绑定到 button 元素的 onClick 事件上。当用户点击按钮时,该函数会被调用,并输出 "Clicked!" 到控制台,同时输出事件对象的 target 标签名,以及参数 name 的值。

相关推荐
LFly_ice3 小时前
学习React-9-useSyncExternalStore
javascript·学习·react.js
gnip4 小时前
js上下文
前端·javascript
中草药z4 小时前
【Stream API】高效简化集合处理
java·前端·javascript·stream·parallelstream·并行流
不知名raver(学python版)4 小时前
npm ERR! code ELIFECYCLE npm ERR! errno 1 npm ERR!
前端·npm·node.js
醉方休4 小时前
React中使用DDD(领域驱动设计)
前端·react.js·前端框架
excel4 小时前
📖 小说网站的预导航实战:link 预加载 + fetch + 前进后退全支持
前端
学习3人组4 小时前
React 样式隔离核心方法和最佳实践
前端·react.js·前端框架
世伟爱吗喽4 小时前
threejs入门学习日记
前端·javascript·three.js
朝阳5814 小时前
用 Rust + Actix-Web 打造“Hello, WebSocket!”——从握手到回声,只需 50 行代码
前端·websocket·rust