Expo Router 中基于文件路由的核心概念

了解 Expo Router 的基本规则以及它与其他代码的关系。


在深入研究如何使用 Expo Router 构建应用的导航树之前,让我们首先了解构成 Expo Router 中基于文件路由基础的核心概念,以及 Expo Router 项目在结构上与其他 React Native 项目有何不同。

🌐 Before diving into how to construct your app's navigation tree with Expo Router, let's first understand the core concepts that make up the foundation of file-based routing in Expo Router, and how an Expo Router project might differ in structure from other React Native projects.

Expo Router 规则

🌐 The rules of Expo Router

1. 所有屏幕/页面都是应用目录中的文件

🌐 1. All screens/pages are files inside of app directory

你应用中的所有导航路径都是由 app 目录中的文件和子目录定义的。app 目录中的每个文件都有一个默认导出,用于定义应用中的不同页面(特殊的 _layout 文件除外)。

🌐 All navigation routes in your app are defined by the files and sub-directories inside the app directory. Every file inside the app directory has a default export that defines a distinct page in your app (except for the special _layout files).

因此,app 内的目录将相关的屏幕分组在一起,可以以堆栈、标签或其他方式排列。

🌐 Accordingly, directories inside app define groups of related screens together as stacks, tabs, or in other arrangements.

2. 所有页面都有一个网址

🌐 2. All pages have a URL

所有页面都有一个 URL 路径,与 app 目录中文件的位置相匹配,可用于在网页的地址栏中导航到该页面,或作为原生移动应用中的特定应用深度链接。这就是 Expo Router 支持“通用深度链接”的含义。无论平台如何,你应用中的所有页面都可以通过 URL 进行导航。

🌐 All pages have a URL path that matches the file's location in the app directory, which can be used to navigate to that page in the address bar on the web, or as an app-specific deep link in a native mobile app. This is what is meant by Expo Router supporting "universal deep-linking". All pages in your app can be navigated to with a URL, regardless of the platform.

3. 首先,index.tsx 是初始路由

🌐 3. First index.tsx is the initial route

使用 Expo Router 时,你无需在代码中定义初始路由或第一个屏幕。相反,当你打开应用时,Expo Router 会寻找与 / URL 匹配的第一个 index.tsx 文件。这可以是 app/index.tsx 文件,但不一定非得是它。如果用户默认应该从导航树的更深层开始,你可以使用 路由组(目录名用括号括起来),这不会算作 URL 的一部分。如果你希望第一个屏幕是一个标签组,你可以将所有标签页面放在 app/(tabs) 目录中,并将默认标签定义为 index.tsx。通过这种安排,/ URL 将直接带用户到 app/(tabs)/index.tsx 文件。

🌐 With Expo Router, you do not define an initial route or first screen in code. Rather, when you open your app, Expo Router will look for the first index.tsx file matching the / URL. This could be an app/index.tsx file, but it doesn't have to be. If the user should start by default in a deeper part of your navigation tree, you can use a route group (a directory where the name is surrounded in parenthesis), and that will not count as part of the URL. If you want your first screen to be a group of tabs, you might put all of the tab pages inside the app/(tabs) directory and define the default tab as index.tsx. With this arrangement, the / URL will take the user directly to app/(tabs)/index.tsx file.

4. Root _layout.tsx 取代 App.jsx/tsx

🌐 4. Root _layout.tsx replaces App.jsx/tsx

每个项目都应该在 app 目录下直接包含一个 _layout.tsx 文件。该文件会在应用中的任何其他路由之前渲染,并且是你放置初始化代码的地方,这些代码以前可能在 App.jsx 文件中,例如加载字体或与启动屏幕交互。

🌐 Every project should have a _layout.tsx file directly inside the app directory. This file is rendered before any other route in your app and is where you would put the initialization code that may have previously gone inside an App.jsx file, such as loading fonts or interacting with the splash screen.

5. 非导航组件位于应用目录之外

🌐 5. Non-navigation components live outside of app directory

在 Expo Router 中,app 目录专用于定义应用的路由。应用的其他部分,如组件、hooks、工具函数等,应放在其他顶层目录中。如果你将非路由文件放在 app 目录中,Expo Router 会尝试将其视为路由处理。

🌐 In Expo Router, the app directory is exclusively for defining your app's routes. Other parts of your app, like components, hooks, utilities, and so on, should be placed in other top-level directories. If you put a non-route inside of the app directory, Expo Router will attempt to treat it like a route.

或者,你可以创建一个 顶层 src 目录,并将你的路由放在 src/app 目录中,非路由组件则放在 src/componentssrc/utils 等文件夹中。这是 Expo Router 识别的唯一其他目录结构。

🌐 Alternatively, you can create a top-level src directory and put your routes inside the src/app directory, with non-route components going in folders like src/components, src/utils, and so on. This is the only other directory structure that Expo Router will recognize.

6. 底层依然是 React Navigation

🌐 6. It's still React Navigation under the hood

虽然这听起来与 React Navigation 有很大不同,但 Expo Router 实际上是建立在 React Navigation 之上的。你可以把 Expo Router 看作是一种 Expo CLI 的优化,它将你的文件结构转换为你之前在代码中定义的 React Navigation 组件。

🌐 While this may sound quite a bit different from React Navigation, Expo Router is actually built on top of React Navigation. You can think of Expo Router as an Expo CLI optimization that translates your file structure into React Navigation components that you previously defined in your own code.

这也意味着你可以经常参考 React Navigation 文档来了解如何设置或配置导航,因为默认的堆栈导航器和标签导航器使用完全相同的选项。

🌐 This also means that you can often refer to React Navigation documentation for how to style or configure navigation, as the default stack and tab navigators use the exact same options.

Expo Router 规则的应用

🌐 The rules of Expo Router applied

让我们运用 Expo Router 的基本规则来快速识别以下项目文件结构的关键元素:

🌐 Let's apply these foundational rules of Expo Router to quickly identify key elements of the following project file structure:

app
index.tsx
home.tsx
_layout.tsx
profile
  friends.tsx
components
TextField.tsx
Toolbar.tsx
  • app/index.tsx 是初始路由,当你打开应用或访问你的网站根 URL 时,它会首先显示。
  • app/home.tsx 是一个路由为 /home 的页面,所以你可以通过浏览器中的 yourapp.com/home 或在原生应用中的 myapp://home 来访问它。
  • app/_layout.tsx 是根布局。你之前可能放在 App.jsx 中的任何初始化代码都应该放在这里。
  • app/profile/friends.tsx 是一个路由为 /profile/friends 的页面。
  • TextField.tsxToolbar.tsx 不在 app 目录中,因此它们不会被视为页面。它们不会有 URL,也不能成为导航操作的目标。不过,它们可以作为组件在 app 目录内的页面中使用。