使

使用 Tailwind 创建 PDF

2025-06-08

使用 Tailwind 创建 PDF

对于开发人员来说,创建 PDF 似乎是一件轻而易举的事。我们用现代工具包在几个小时内就能构建前端,静态文档还有什么比这更难的呢?

PDF 是由 Adob​​e 于 1993 年发明的一种跨平台文档格式。该格式本身侧​​重于可移植性而非交互性——一种正交于 HTML 和 CSS 的方法。后者定义了一种盒子模型,而前者则采用了命令式方法。简而言之,HTML 矩形在 PDF 中由 4 条线组成。

这种方法正是 PDF 的优势所在,也是它被广泛使用的原因:它看起来总是一样。而 HTML 则依赖于许多因素,从屏幕尺寸到浏览器版本。如果我们能将 HTML 的布局功能移植到 PDF 中,会怎么样呢?

使用 React 和 Tailwind 创建你的第一个 PDF

开源库react-print-pdf带来了一组组件和包装器,我们可以用它们在几分钟内构建漂亮的 PDF。

编译为 HTML

Tailwind 的挑战在于它是一个动态 CSS 框架。它依赖于 JavaScript 运行时来生成最终的 CSS。这对于 PDF 生成来说是一个问题,因为我们需要静态文件。我们将首先转换为静态 HTML,然后再转换为 PDF。

为此,我们将使用<Tailwind>中的组件react-print-pdf。该组件将检测所有 Tailwind 类并生成最终的 CSS。然后,我们可以使用该compile函数将 React 树转换为 HTML。

import { Tailwind, Footnote, compile } from "@fileforge/react-print";

const getHTML = async () => {
  return compile(
    <Tailwind>
      <h1 className="text-4xl font-bold">
        Invoice #123
        <Footnote>
          <p className="text-sm">This is a demo invoice</p>
        </Footnote>
      </h1>
    </Tailwind>
  );
};
Enter fullscreen mode Exit fullscreen mode

当调用时getHTML,我们将得到以下HTML:

<!doctype html>
<html>
  <head>
    <style>
      .text-4xl {
        font-size: 2.25rem;
        line-height: 2.5rem;
      }
      .font-bold {
        font-weight: 700;
      }
      .text-sm {
        font-size: 0.875rem;
        line-height: 1.25rem;
      }
    </style>
  </head>
  <body>
    <h1 class="text-4xl font-bold">
      Invoice #123
      <div class="footnote">
        <p class="text-sm">This is a demo invoice</p>
      </div>
    </h1>
  </body>
</html>
Enter fullscreen mode Exit fullscreen mode

将 HTML 转换为 PDF

有几种方法可以将此 HTML 转换为 PDF:

  • 使用 Fileforge 作为客户端或服务器端 API,它将支持所有功能,例如页眉、页脚和页码。
  • 如果在客户端,您可以react-to-print使用浏览器的打印对话框。这是一个便宜的选择,但不支持高级功能,并且可能会引入很多视觉错误。
  • 使用服务器端无头浏览器(例如 Gotenberg)puppeteer将 HTML 转换为 PDF。这是最可靠的免费选项,但需要服务器。如果您需要在生产环境中使用它,我们建议您使用Gotenberg

以下是如何使用 Fileforge 将 HTML 转换为 PDF 的示例:

import { FileforgeClient } from "@fileforge/client";
import { getHTML } from "./getHTML";
import fs from "fs";

const ff = new FileforgeClient({
  apiKey: process.env.FILEFORGE_API_KEY
});

const { file } = await ff.pdf.generate(await getHTML());

file.pipe(fs.createWriteStream("invoice.pdf");
Enter fullscreen mode Exit fullscreen mode

就这样!现在,你的 React 应用已经生成了一张漂亮的 PDF 发票。你可以使用 Tailwind 的大部分功能以及 Tailwind 中的组件来react-print-pdf创建高级布局。查看文档了解更多信息。

底层:动态样式

如果你已经读到这里,你可能会好奇动态样式是如何转换为静态 CSS 的。Tailwind 是一个实用优先的框架,因此它带来了一系列特定的挑战。让我们来看看 Tailwind 的常规生成流程:

  1. Tailwind 解析您指定的文件tailwind.config.js并生成一组类。
  2. 然后它使用 PostCSS 插件将 CSS 中的类替换为实际样式。
  3. 然后,它使用 JavaScript 运行时生成最终的 CSS,并对其进行重复数据删除和缩小。

作为构建工具,它运行良好,但将即时编译功能引入 PDF 生成却是一项挑战。在无服务器和浏览器环境中,没有文件系统,我们需要检测 React 树中的动态类。

Tailwind 组件使用的方法与 中的方法类似react-email。Tailwind React 组件会解析其子标签并检测类。然后,它使用浏览器版本的 Tailwind 生成最终的 CSS。最后,它会将其注入到 HTML 中。这听起来并不简单!

这篇博文最初发布在Fileforge 博客上。

鏂囩珷鏉ユ簮锛�https://dev.to/fileforge/create-pdfs-with-tailwind-k0
PREV
哪些颜色在黑白背景上看起来好看?那么,色彩对比度是如何计算的呢?相对亮度又是如何计算的呢?让我们来算一算!颜色列表
NEXT
我的编程之旅 - 编程战士