跳到主要内容

React 基础

React Native 运行在 React 之上,React 是一个流行的开源库,用于使用 JavaScript 构建用户界面。为了充分利用 React Native,了解 React 本身会有所帮助。本节可以帮助你入门,也可以作为复习课程。

我们将介绍 React 背后的核心概念

  • 组件
  • JSX
  • props
  • state

如果你想深入了解,我们鼓励你查看 React 的官方文档

你的第一个组件

本 React 介绍的其余部分在其示例中使用了猫:友善、平易近人的生物,需要名字和一家工作的咖啡馆。这是你的第一个 Cat 组件

以下是你的操作方法:要定义你的 Cat 组件,首先使用 JavaScript 的 import 导入 React 和 React Native 的 Text 核心组件

tsx
import React from 'react';
import {Text} from 'react-native';

你的组件从一个函数开始

tsx
const Cat = () => {};

你可以将组件视为蓝图。函数组件返回的任何内容都将渲染为 React 元素。 React 元素让你描述你想要在屏幕上看到的内容。

在这里,Cat 组件将渲染一个 <Text> 元素

tsx
const Cat = () => {
return <Text>Hello, I am your cat!</Text>;
};

你可以使用 JavaScript 的 export default 导出你的函数组件,以便在你的应用程序中像这样使用

tsx
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")}

你可以将花括号视为在 JSX 中创建通往 JS 功能的门户!

因为 JSX 包含在 React 库中,所以如果你在文件顶部没有 import React from 'react',它将无法工作!

自定义组件

你已经了解了 React Native 的核心组件。React 允许你将这些组件相互嵌套以创建新组件。这些可嵌套、可重用的组件是 React 范例的核心。

例如,你可以将 TextTextInput 嵌套在下面的 View 中,React Native 会将它们一起渲染

开发者 notes

如果你熟悉 Web 开发,<View><Text> 可能会让你想起 HTML!你可以将它们视为应用程序开发的 <div><p> 标签。

你可以通过使用 <Cat> 多次且在多个位置渲染此组件,而无需重复你的代码

任何渲染其他组件的组件都是一个 父组件。 在这里,Cafe 是父组件,每个 Cat 都是一个 子组件。

你可以在你的咖啡馆里放任意多只猫。每个 <Cat> 渲染一个独特的元素——你可以使用 props 自定义它。

Props

Props 是 “properties”(属性)的缩写。Props 让你自定义 React 组件。例如,在这里你为每个 <Cat> 传递一个不同的 name,供 Cat 渲染

React Native 的大多数核心组件也可以使用 props 进行自定义。例如,当使用 Image 时,你传递给它一个名为 source 的 prop,以定义它显示的图像

Image许多不同的 props,包括 style,它接受一个设计和布局相关的属性-值对的 JS 对象。

请注意围绕 style 的 width 和 height 的双重花括号 {{ }}。在 JSX 中,JavaScript 值使用 {} 引用。如果你要传递除字符串之外的其他内容作为 props,例如数组或数字,这将非常方便:<Cat food={["fish", "kibble"]} age={2} />。但是,JS 对象 用花括号表示:{width: 200, height: 200}。因此,要在 JSX 中传递 JS 对象,你必须将该对象包装在 另一对 花括号中:{{width: 200, height: 200}}

你可以使用 props 和核心组件 TextImageView 构建许多东西!但是要构建交互式的东西,你需要 state。

State

虽然你可以将 props 视为用于配置组件渲染方式的参数,但 state 就像组件的个人数据存储。State 对于处理随时间变化或来自用户交互的数据很有用。State 为你的组件提供记忆!

作为一般规则,使用 props 在组件渲染时对其进行配置。使用 state 跟踪你期望随时间变化的任何组件数据。

以下示例发生在一家猫咖啡馆中,两只饥饿的猫正在等待喂食。它们的饥饿感(我们期望它会随时间变化,不像它们的名字)存储为 state。要喂猫,请按下它们的按钮——这将更新它们的状态。

你可以通过调用 React 的 useState Hook 向组件添加状态。Hook 是一种函数,可让你 “hook into” React 功能。例如,useState 是一个 Hook,可让你向函数组件添加状态。你可以在 React 文档中了解有关其他类型的 Hook 的更多信息。

首先,你将需要从 React 导入 useState,如下所示

tsx
import React, {useState} from 'react';

然后,通过在其函数内部调用 useState 来声明组件的状态。在此示例中,useState 创建了一个 isHungry 状态变量

tsx
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 prop

tsx
<Button
onPress={() => {
setIsHungry(false);
}}
//..
/>

现在,当有人按下按钮时,onPress 将触发,调用 setIsHungry(false)。这将状态变量 isHungry 设置为 false。当 isHungry 为 false 时,Buttondisabled prop 将设置为 true,并且其 title 也会更改

tsx
<Button
//..
disabled={!isHungry}
title={isHungry ? 'Give me some food, please!' : 'Thank you!'}
/>

你可能已经注意到,尽管 isHungry 是一个 const,但它似乎是可重新赋值的!发生的事情是,当调用状态设置函数(如 setIsHungry)时,其组件将重新渲染。在这种情况下,Cat 函数将再次运行——这一次,useState 将为我们提供 isHungry 的下一个值。

最后,将你的猫放在 Cafe 组件中

tsx
const Cafe = () => {
return (
<>
<Cat name="Munkustrap" />
<Cat name="Spot" />
</>
);
};

看到上面的 <></> 吗?这些 JSX 位是 fragments。相邻的 JSX 元素必须包装在封闭标签中。Fragments 允许你这样做,而无需嵌套额外的、不必要的包装元素(如 View)。


既然你已经了解了 React 和 React Native 的核心组件,让我们通过查看 处理 <TextInput> 来更深入地了解其中一些核心组件。