React 基础
本页面由 PageTurner AI 翻译(测试版)。未经项目官方认可。 发现错误? 报告问题 →
React Native 基于 React 运行——这是一个流行的开源 JavaScript 用户界面库。要充分发挥 React Native 的潜力,理解 React 本身至关重要。本节既适合初学者入门,也可供经验丰富的开发者复习。
我们将介绍 React 的核心概念:
-
components(组件)
-
JSX
-
props(属性)
-
state(状态)
如需深入学习,建议查阅 React 官方文档。
创建第一个组件
在接下来的 React 介绍中,我们将以猫为例:这些友好亲切的小家伙需要名字和工作的咖啡馆。下面是您第一个 Cat 组件:
创建 Cat 组件的步骤如下:首先使用 JavaScript 的 import 导入 React 和 React Native 的 Text 核心组件:
import React from 'react';
import {Text} from 'react-native';
组件以函数形式开始:
const Cat = () => {};
您可以将组件视为设计蓝图。函数组件返回的内容会被渲染为 React 元素,这些元素描述了您希望在屏幕上显示的内容。
这里的 Cat 组件将渲染一个 <Text> 元素:
const Cat = () => {
return <Text>Hello, I am your cat!</Text>;
};
使用 JavaScript 的 export default 导出函数组件,即可在整个应用中使用:
const Cat = () => {
return <Text>Hello, I am your cat!</Text>;
};
export default Cat;
这是导出组件的多种方式之一。这种方式与 Snack Player 兼容良好。但根据应用的文件结构,可能需要采用其他约定。这份 JavaScript 导入导出速查表 会很有帮助。
现在仔细观察 return 语句。<Text>Hello, I am your cat!</Text> 使用了特殊的 JavaScript 语法 JSX,它让编写元素更加便捷。
JSX
React 和 React Native 使用 JSX 语法,允许您在 JavaScript 中直接书写元素:<Text>Hello, I am your cat!</Text>。React 文档提供了 全面的 JSX 指南。由于 JSX 本质是 JavaScript,您可以在其中使用变量。例如声明猫咪名字 name 并用花括号嵌入 <Text>。
花括号内可嵌入任何 JavaScript 表达式,包括函数调用 {getFullName("Rum", "Tum", "Tugger")}:
- TypeScript
- JavaScript
您可以将花括号视为连接 JSX 与 JavaScript 功能的传送门!
由于 JSX 包含在 React 库中,若文件顶部没有 import React from 'react',JSX 将无法工作!
自定义组件
您已了解过 React Native 核心组件。React 允许将这些组件相互嵌套来创建新组件,这种可嵌套、可复用的组件正是 React 范式的核心。
例如,您可以在下面的 View 中嵌套 Text 和 TextInput,React Native 会将它们一并渲染:
开发者说明
- Android
- Web
If you’re familiar with web development, <View> and <Text> might remind you of HTML! You can think of them as the <div> and <p> tags of application development.
On Android, you usually put your views inside LinearLayout, FrameLayout, RelativeLayout, etc. to define how the view’s children will be arranged on the screen. In React Native, View uses Flexbox for its children’s layout. You can learn more in our guide to layout with Flexbox.
通过使用 <Cat> 组件,您可以在多个位置多次渲染而无需重复代码:
任何渲染其他组件的组件都是父组件。在这里,Cafe 是父组件,而每个 Cat 是一个子组件。
你可以在咖啡馆里放任意数量的猫咪。每个 <Cat> 都会渲染一个独特的元素——你可以通过 props 来自定义它们。
属性
Props(属性)是 "properties" 的缩写。Props 让你能够自定义 React 组件。例如,这里你为每个 <Cat> 传递不同的 name 供 Cat 渲染:
- TypeScript
- JavaScript
大多数 React Native 核心组件也可以通过 props 自定义。例如,使用 Image 组件时,你可以传递名为 source 的 prop 来指定显示的图片:
Image 组件有多种不同 props,包括 style——它接受包含设计和布局相关属性值对的 JavaScript 对象。
注意 style 属性值周围的双层花括号 {{ }}。在 JSX 中,JavaScript 值通过 {} 引用。当传递非字符串类型的属性(如数组或数字)时这很方便:<Cat food={["fish", "kibble"]} age={2} />。但请注意:JS 对象同样使用花括号表示:{width: 200, height: 200}。因此要在 JSX 中传递 JS 对象,必须用额外一层花括号包裹:{{width: 200, height: 200}}
通过 props 和核心组件 Text、Image、View,你可以构建许多功能!但要实现交互效果,就需要使用状态。
状态
你可以将 props 视为配置组件渲染方式的参数,而状态则像是组件的个人数据存储器。状态适用于处理随时间变化的数据或用户交互数据,它赋予组件记忆能力!
通用原则:使用属性(props)配置组件的初始渲染,使用状态(state)跟踪预期随时间变化的组件数据。
下面示例发生在猫咖啡馆:两只饥饿的猫咪等待喂食。它们的饥饿状态(预期会随时间变化,不像名字)被存储为状态。按下按钮喂猫——这将更新它们的状态。
通过调用 React 的 useState Hook 可为组件添加状态。Hook 是一种让你"挂钩"React 功能的函数。例如 useState 就是能为函数组件添加状态的 Hook。你可以在 React 文档了解其他 Hook。
- TypeScript
- JavaScript
首先需要从 React 导入 useState:
import React, {useState} from 'react';
然后在组件函数内调用 useState 来声明状态。本示例中,useState 创建了 isHungry 状态变量:
const Cat = (props: CatProps) => {
const [isHungry, setIsHungry] = useState(true);
// ...
};
useState 可追踪任何数据类型:字符串、数字、布尔值、数组、对象等。例如可通过 const [timesPetted, setTimesPetted] = useState(0) 追踪猫咪被抚摸的次数!
调用 useState 会完成两件事:
-
创建带有初始值的"状态变量"——本例中状态变量是
isHungry,初始值为true -
创建设置该状态变量值的函数——
setIsHungry
命名没有限制。但将模式视为 [<getter>, <setter>] = useState(<initialValue>) 会更便于理解。
接下来添加 Button 核心组件并赋予它 onPress 属性:
<Button
onPress={() => {
setIsHungry(false);
}}
//..
/>
现在,当用户按下按钮时,onPress 事件会触发并调用 setIsHungry(false)。这将状态变量 isHungry 设为 false。当 isHungry 为 false 时,Button 的 disabled 属性会被设置为 true,同时 title 属性也会相应变化:
<Button
//..
disabled={!isHungry}
title={isHungry ? 'Give me some food, please!' : 'Thank you!'}
/>
你可能注意到,尽管 isHungry 是用 const 声明的,但它似乎可以被重新赋值!
这里的 const 关键字并不意味着状态本身不可变,而是表示包含状态及其更新函数的对象引用不会改变。
实际情况是:当调用状态设置函数(如 setIsHungry)时,其所在组件会重新渲染。此时 Cat 函数将再次执行——而这一次,useState 会返回 isHungry 的新值。
最后,将你的猫咪组件放入 Cafe 组件中:
const Cafe = () => {
return (
<>
<Cat name="Munkustrap" />
<Cat name="Spot" />
</>
);
};
看到上面的 <> 和 </> 了吗?这些 JSX 片段是 fragments。相邻的 JSX 元素必须包裹在一个闭合标签中。Fragments 允许你这样做,而无需嵌套额外的、不必要的包裹元素(例如 View)。
现在你已经掌握了 React 和 React Native 的核心组件,接下来让我们通过 处理 <TextInput> 更深入地探索这些核心组件。