跳到主要内容
新架构实战课 实操 + 基建 + 原理全维度包揽,抢先掌握 React Native 新架构精髓 立即查看 >Version: Next

使用 TypeScript

TypeScript 是一种通过添加类型定义来扩展 JavaScript 的语言。新的 React Native 项目默认以 TypeScript 为目标,同时也支持 JavaScript 和 Flow。

使用 TypeScript 开始新项目

React Native CLI 创建的新项目或使用 Ignite 等流行模板将默认使用 TypeScript。

TypeScript 也可以与 Expo 一起使用,Expo 维护 TypeScript 模板,或者当向项目添加 .ts.tsx 文件时,Expo 将提示您自动安装和配置 TypeScript。

npx create-expo-app --template

在已有的项目中添加 TypeScript

  1. 将 TypeScript,类型文件,以及 ESLint 插件等依赖添加到项目中。
npm install -D @tsconfig/react-native @types/jest @types/react @types/react-test-renderer typescript
note

该命令添加了每个依赖项的最新版本。版本可能需要更改,以匹配项目使用的现有软件包。您可以使用类似 React Native Upgrade Helper 的工具查看 React Native 提供的版本。

  1. 添加一个 TypeScript 配置文件。在项目的根目录中创建一个tsconfig.json
{
"extends": "@tsconfig/react-native/tsconfig.json"
}
  1. 将 JavaScript 文件重命名为* .tsx:

请保留./index.js入口文件,否则可能将在打包生产版本时遇到问题。

  1. 运行 tsc 对 TypeScript 文件进行类型检查。
npx tsc

使用 JavaScript 而非 TypeScript

React Native 将新应用默认设置为 TypeScript,但仍可使用 JavaScript。具有 .jsx.js 扩展名的文件将被视为 JavaScript 而非 TypeScript,并且不会进行类型检查。TypeScript 模块仍可导入 JavaScript 模块,反之亦然。

TypeScript 和 React Native 是如何工作的

无需额外配置,和非 TypeScript 的 React Native 项目一样都是直接通过 Babel 将您的文件转换为 JavaScript。我们建议您只使用 TypeScript 编译器tsc的类型检查功能(而不是编译)。如果您有已经存在的 TypeScript 代码需要迁移到 React Native,这里有一些关于使用 Babel 而不是 TypeScript 编译器的注意事项

用 TypeScript 写 React Native 的示例

可以用interface来为 React 的函数组件编写Props的类型(使用React.FC<Props>)。这样在后续编码的过程中,编辑器就会根据这一类型来做类型检查并提供自动补全。

components/Hello.tsx
import React from 'react';
import {Button, StyleSheet, Text, View} from 'react-native';

export type Props = {
name: string;
baseEnthusiasmLevel?: number;
};

const Hello: React.FC<Props> = ({
name,
baseEnthusiasmLevel = 0,
}) => {
const [enthusiasmLevel, setEnthusiasmLevel] = React.useState(
baseEnthusiasmLevel,
);

const onIncrement = () =>
setEnthusiasmLevel(enthusiasmLevel + 1);
const onDecrement = () =>
setEnthusiasmLevel(
enthusiasmLevel > 0 ? enthusiasmLevel - 1 : 0,
);

const getExclamationMarks = (numChars: number) =>
numChars > 0 ? Array(numChars + 1).join('!') : '';

return (
<View style={styles.container}>
<Text style={styles.greeting}>
Hello {name}
{getExclamationMarks(enthusiasmLevel)}
</Text>
<View>
<Button
title="Increase enthusiasm"
accessibilityLabel="increment"
onPress={onIncrement}
color="blue"
/>
<Button
title="Decrease enthusiasm"
accessibilityLabel="decrement"
onPress={onDecrement}
color="red"
/>
</View>
</View>
);
};

const styles = StyleSheet.create({
container: {
flex: 1,
alignItems: 'center',
justifyContent: 'center',
},
greeting: {
fontSize: 20,
fontWeight: 'bold',
margin: 16,
},
});

export default Hello;

你可以在TypeScript playground中更深入地探索语法。

参考资料(英文)

在 TypeScript 中使用自定义路径别名

To use custom path aliases with TypeScript, you need to set the path aliases to work from both Babel and TypeScript. Here's how:

  1. Edit your tsconfig.json to have your custom path mappings. Set anything in the root of src to be available with no preceding path reference, and allow any test file to be accessed by using tests/File.tsx:
{
- "extends": "@tsconfig/react-native/tsconfig.json"
+ "extends": "@tsconfig/react-native/tsconfig.json",
+ "compilerOptions": {
+ "baseUrl": ".",
+ "paths": {
+ "*": ["src/*"],
+ "tests": ["tests/*"],
+ "@components/*": ["src/components/*"],
+ },
+ }
}
  1. Add babel-plugin-module-resolver as a development package to your project:
npm install --save-dev babel-plugin-module-resolver
  1. Finally, configure your babel.config.js (note that the syntax for your babel.config.js is different from your tsconfig.json):
{
presets: ['module:metro-react-native-babel-preset'],
+ plugins: [
+ [
+ 'module-resolver',
+ {
+ root: ['./src'],
+ extensions: ['.ios.js', '.android.js', '.js', '.ts', '.tsx', '.json'],
+ alias: {
+ tests: ['./tests/'],
+ "@components": "./src/components",
+ }
+ }
+ ]
+ ]
}