Next.js + Tailwind 深色模式:从原理到最佳实践

Background

实现个人网站的过程中,想要实现深色模式,在网上没找到合适的开箱即用解决方案,所以决定自己实现一个。

1. 深色模式是什么

自己看MDN

这里只总结几个关键点

  • 深色模式是系统级的,网站应该遵循系统主题,
  • 但同时也应该可以手动设置满足一些个性化需要
  • 深色模式不应该影响网站的可用性,比如可访问性,因此字体颜色等需要根据深色模式进行调整
  • 深色模式不应该影响网站的性能,因此不应该使用图片来实现深色模式,而是应该使用CSS来实现
  • 需要尽可能提前设置深色模式,以避免闪烁(FOUC)

根据这些原则,可以总结出几种方式,这里只记录我实现的方式

2. 最佳实践

Step 1: 设置 color-scheme 来标识网站支持深色模式

Loading...

tailwind.config.ts 中设置 darkMode: "class",以启用 Tailwind 的类模式。这样,在 HTML 标签中添加 dark 类,就可以应用深色模式。而不是使用 color-scheme 来标识网站支持深色模式。

Loading...

Step 2: 根据系统主题设置初始主题,以避免闪烁(FOUC)

Loading...

在 Next.js 中,app/layout.tsx 是全局布局组件,因此可以在这里设置初始主题,以避免闪烁(FOUC)。 如果是 Page Router ,则应该使用 _document.tsx 来设置初始主题。但这里仅讨论 App Router 的情况(因为我是用的 App Router)。

Step 3: 增加深色模式切换按钮,让用户可以手动切换深色模式

Loading...

app/providers.tsx 中,我们创建了一个 ThemeProvider 组件,并导出了 useTheme 钩子,以便在其他组件中使用。 接下来我们就可以在其他组件中使用 useTheme 钩子来获取和设置主题了。

Loading...

我们通过 useTheme 钩子来获取和设置主题,并通过 setTheme 函数来切换主题。

Step 4: 设置页面样式

在 CSS 中如何分别设置深色模式和浅色模式

Loading...

在 TSX 中如何设置深色模式

Loading...