什么是转换矩阵以及如何使用它

项目地址:

Pdfium.Net:https://github.com/1000374/Pdfium.Net.Free

PdfiumViewer:https://github.com/1000374/PdfiumViewer

Pdfium.Net.Free 支持

  • .NETFramework 4.0

  • .NETFramework 4.5

  • .NETStandard 2.0

  • .Net8.0

可以和PdfiumViewer.Free共同使用预览、编辑pdf,也可以直接引用Pdfium.Net.Free 操作pdf,Pdfium.Net.Free封装了现有Pdfium的函数,实现了部分操作pdf的功能,部分功能等待后续~~

当您使用 PDFium 库处理 PDF 文件中的对象时,您可以使用 SetMatrix 函数以各种方式转换对象(通常是图像,但也包括任何其他嵌入对象)。使用变换矩阵,您可以旋转、平移(移动)、缩放或剪切图像。可以在此处找到使用矩阵将图像缩放到 PDF 文档中页面大小的示例。

本文更深入地解释了什么是转换矩阵,以及为什么它的工作方式如此。

 矩阵

简介

如果您对线性代数非常陌生,那么矩阵只是一组值,它们组合在一起形成矩形或正方形。以下是矩阵的示例:

 许多物理值可以(并且通常)以矩阵形式表示。例如,坐标;它们通常表示为向量 - 一个矩阵,其中包含一列和每个空间维度的行数(2D 为 2 行,3D 为 3 行,依此类推)。这种矩阵中的每个元素都是相应轴上的坐标。向量的示例如上所示。

PDF 文档也使用坐标系。这两个轴是页面的垂直和水平尺寸,每个坐标表示该轴上的 PDF 点数。因此,如果页面上的给定对象放置在距底部 3500 个点和从左侧 100 个点处,则其坐标向量为:

,这本质上是相同的。

 

矩阵可以像普通数字一样求和、减去、乘法和除法(反转)。加法和减法是最简单的操作,这里是示例:

加法、减法


要将一个矩阵添加到另一个矩阵,您应该简单地将第一个矩阵的每个元素添加到第二个矩阵的相应元素中。当然,矩阵必须具有相等的维度。

 减法 除了算术符号之外,减法也是如此:

 加法和减法是可交换的。您可以更改矩阵的顺序,但仍然得到相同的结果(减法时的算术符号除外):

A + B = B + A A - B = -(B - A)其中 A和 B 是矩阵。

 


乘法矩阵是一个更棘手的过程。要将矩阵 A 乘以矩阵 B,应将第一个矩阵的每一行乘以第二个矩阵的每一列。每个这样的乘积都是在(i,j)位置所得矩阵的元素。其中 i 是 A 中行的索引,j 是 B 中列的索引。
听起来很复杂?下面是一个示例:

 首先,我们将第一个矩阵的第一行乘以第二个矩阵的第一列。这为我们提供了结果矩阵中 (1,1) 处的元素:然后,我们将第二行和第一列相乘以计算 (1,2) 处的元素:然后,我们计算 (2,1) 处的元素:最后是 (2,2) 处的元素:

 

 

 

 矩阵的相乘方式有两个重要影响:

    1. A 的列数必须与 B 的行数匹配。如上所示,您可以使用多个 2×2 和 2×2 矩阵。您还可以将 2×6 到 4×2(结果为 6×4 矩阵)或 3×3 到 1×3(结果为 3×3 矩阵)。但是,例如,您不能将 3 乘以 3 乘以 1 乘 2。
    2. 矩阵的乘法不是交换的。.

如果以上面的例子为例,改变矩阵的顺序,结果会有所不同,即:

 

 除法

如果您认为矩阵的乘法很难理解,那么我们有个坏消息要告诉您:将它们相乘更加棘手。但是,您不需要划分矩阵来执行 PDF 对象的转换,可查看百度百科: https://baike.baidu.com/item/%E5%8F%AF%E9%80%86%E7%9F%A9%E9%98%B5/11035614?fr=ge_ala

 

什么是变换矩阵

PDF 在二维坐标系中表示其内容。每个点的坐标都可以表示为向量:(x, y)。 变换矩阵允许更改默认坐标系并将原始坐标 (x, y) 映射到这个新坐标系:(x', y')。根据我们改变坐标系的方式,我们以这种方式有效地旋转、缩放、移动(平移)或剪切对象。

变换矩阵是一个 3×3 矩阵:

 矩阵的元素对应于各种变换(见下文)。要变换坐标系,应将原始坐标向量乘以变换矩阵。由于矩阵是 3×3,向量是 1×2,我们需要向它添加一个元素,使向量的大小与乘法规则要求的矩阵匹配(见上文)。

话虽如此,转换后的向量如下:

 例如,要在页面的位图上旋转图像,PDF 渲染器应获取图像每个点的坐标,使用上述公式更改它们,并在新坐标处渲染该像素。


这就是调用 SetMatrix 函数时要执行的操作:告诉呈现器应如何转换对象的每个渲染像素。

变换操作

移 :
将坐标系移动给定偏移量。该操作将生成一个新坐标系,该坐标系沿 x 轴移动 e,沿 y 轴移动 f。

平移操作的变换矩阵为:示例:

 原始坐标系中点的坐标为 (240 651 1)。我们想将坐标系向左平移 10 个点,向上平移 20 个点。所需的变换矩阵为:生成的坐标为:

 

 如您所见,坐标已按计划更改。图像的所有其他像素的转换方式相同。

要传递给 SetMatrix 方法的参数包括:

 

SetMatrix(1, 0, 0, 1, -10, 20).

  

 缩放:

缩放放一个对象,我们需要更改它的一个维度或两个维度。

尺度运算的变换矩阵为:

 式中 a 和 d 分别是水平和垂直尺度因子。如果它们大于 1,则对象将按比例放大。如果它们小于 1,则对象将从其原始大小缩小。

示例:

 此矩阵将对象沿 x 轴向上放大 40%,沿 y 轴向下缩放 20%。

SetMatrix(1.4, 0, 0, 0.8, 0, 0)

 翻转/反射

此操作类似于缩放。我们只需要反转其中一个坐标进行水平/垂直翻转或两者兼而有之,以反映原点。

  

 水平翻转:

SetMatrix(-1, 0, 0, 1, 0, 0)

垂直翻转:

SetMatrix(1, 0, 0, -1, 0, 0)

中央翻转:

SetMatrix(-1, 0, 0, -1, 0, 0)

 

旋转:

旋转操作将给定角度的顺时针或逆时针旋转原始坐标系。

旋转操作的矩阵为:

 

 
其中是旋转角度。

矩阵的形式来自简单的三角函数,但形式证明超出了本文的范围。

假设我们想将一个对象顺时针旋转 30 度。然后,对象的每个像素都按如下方式进行转换:

 

SetMatrix(0.87, -0.5, 0.5, 0.87, 0, 0)

  

 剪切

x 方向剪切的变换矩阵为:假设我们想将对象剪切 20 个 PDF 点对:

 

 

SetMatrix(1, 0, 20, 1, 0, 0)

 对于 y 方向的剪切:将物体剪切 45 PDF 指向下方:

 

 

SetMatrix(1, -45, 0, 1, 0, 0)

 多个转换

如果需要对同一对象应用多个转换,该怎么办?比如,扩大规模和轮换?或者水平翻转镜像图像并将其转换为页面上的所需位置?

在这种情况下,您只需要几个变换矩阵。为了执行一系列变换,将各个变换的矩阵相乘。然而,如上所述,乘法运算不是可交换的,因此变换矩阵的顺序有很大的不同。

例如,如果要旋转对象,然后平移它,则生成的变换矩阵为:对于变换矩阵的相反顺序,生成的矩阵是不同的:

 

 第一次可能看起来不明显。您可以将对象移动 10 厘米,然后将其旋转 45 度。或者您可以将其旋转 45 度,然后将旋转的对象移动 10 厘米。为什么会有这种差异?由于变换矩阵不会旋转(平移、缩放等)对象,因此它会旋转包含对象的坐标系

这样想吧。把一支铅笔放在桌子上。当您变换对象时,变换的顺序将是“将铅笔旋转 45 度,然后向左移动 10 厘米”。但是当你变换坐标系时,你会得到“将桌子旋转 45 度,然后将桌子向左移动 10 厘米”。

 结论

现在您知道FS_MATRIX中的这些 a、b、c、d、e 和 f 系数是什么意思了。由这些元素组成的转换矩阵允许几乎任意调整任何 PDF 位图或其他对象。

  

 

posted @ 2024-02-24 16:38  小树禾小央  阅读(381)  评论(0编辑  收藏  举报