【问题标题】:Image auto resizes in PdfPCell with iTextSharp使用 iTextSharp 在 PdfPCell 中自动调整图像大小
【发布时间】:2026-01-31 00:35:02
【问题描述】:

我对 iTextSharp 库中的图像有一个奇怪的问题。 我将图像添加到 PdfPCell 并且由于某种原因它被放大了。 如何保持原来的大小?

我虽然打印时图像会相同,但图片上的差异在打印版本上是相同的。必须使用 ScaleXXX 手动缩放图像以使其正确似乎有点不合逻辑,并且不会产生好的结果。

那么如何将图像以其原始大小放入表格的 PdfPCell 中而无需缩放?

这是我的代码:

private PdfPTable CreateTestPDF()
{
    PdfPTable table = new PdfPTable(1);
    table.WidthPercentage = 100;

    Phrase phrase = new Phrase("MY TITLE", _font24Bold);
    table.AddCell(phrase);

    PdfPTable nestedTable = new PdfPTable(5);
    table.WidthPercentage = 100;

    Phrase cellText = new Phrase("cell 1", _font9BoldBlack);
    nestedTable.AddCell(cellText);

    cellText = new Phrase("cell 2", _font9BoldBlack);
    nestedTable.AddCell(cellText);

    cellText = new Phrase("cell 3", _font9BoldBlack);
    nestedTable.AddCell(cellText);

    iTextSharp.text.Image image = iTextSharp.text.Image.GetInstance(@"d:\MyPic.jpg");
    image.Alignment = iTextSharp.text.Image.ALIGN_CENTER;
    PdfPCell cell = new PdfPCell(image);
    cell.HorizontalAlignment = PdfPCell.ALIGN_MIDDLE;
    nestedTable.AddCell(cell);

    cellText = new Phrase("cell 5", _font9BoldBlack);
    nestedTable.AddCell(cellText);

    nestedTable.AddCell("");

    string articleInfo = "Test Text";
    cellText = new Phrase(articleInfo, _font8Black);
    nestedTable.AddCell(cellText);

    nestedTable.AddCell("");
    nestedTable.AddCell("");
    nestedTable.AddCell("");

    table.AddCell(nestedTable);
    SetBorderSizeForAllCells(table, iTextSharp.text.Rectangle.NO_BORDER);
    return table;
}

static BaseColor _textColor = new BaseColor(154, 154, 154);
iTextSharp.text.Font _font8 = new iTextSharp.text.Font(iTextSharp.text.Font.FontFamily.HELVETICA, 8, iTextSharp.text.Font.NORMAL, _textColor);
iTextSharp.text.Font _font8Black = new iTextSharp.text.Font(iTextSharp.text.Font.FontFamily.HELVETICA, 8, iTextSharp.text.Font.NORMAL, BaseColor.BLACK);
iTextSharp.text.Font _font9 = new iTextSharp.text.Font(iTextSharp.text.Font.FontFamily.HELVETICA, 9, iTextSharp.text.Font.NORMAL, _textColor);
iTextSharp.text.Font _font9BoldBlack = new iTextSharp.text.Font(iTextSharp.text.Font.FontFamily.HELVETICA, 9, iTextSharp.text.Font.BOLD, BaseColor.BLACK);
iTextSharp.text.Font _font10 = new iTextSharp.text.Font(iTextSharp.text.Font.FontFamily.HELVETICA, 10, iTextSharp.text.Font.NORMAL, _textColor);
iTextSharp.text.Font _font10Black = new iTextSharp.text.Font(iTextSharp.text.Font.FontFamily.HELVETICA, 10, iTextSharp.text.Font.NORMAL, BaseColor.BLACK);
iTextSharp.text.Font _font10BoldBlack = new iTextSharp.text.Font(iTextSharp.text.Font.FontFamily.HELVETICA, 10, iTextSharp.text.Font.BOLD, BaseColor.BLACK);
iTextSharp.text.Font _font24Bold = new iTextSharp.text.Font(iTextSharp.text.Font.FontFamily.HELVETICA, 24, iTextSharp.text.Font.BOLD, _textColor);

【问题讨论】:

  • 你使用的是什么版本的 iTextSharp?
  • 斯洛文尼亚凌晨 4 点。你经常睡觉吗? :)
  • 实际上已经是凌晨 5 点了。这是我深入研究某事,忘记时间,跳过夜晚的那些夜晚之一:)
  • @MladenPrajdic 你能修复图像吗?

标签: c# itext pdf-generation


【解决方案1】:

我正在使用 iTextSharp v4.1.2,我得到以下行为:

使用此代码,通过 AddCell 方法将图像直接添加到表格中,图像被放大以适合单元格:

nestedTable.AddCell(image);

使用此代码,将图像添加到单元格中,然后将单元格添加到表格中,图像以其原始大小显示:

PdfPCell cell = new PdfPCell(image);
cell.HorizontalAlignment = PdfPCell.ALIGN_CENTER;
nestedTable.AddCell(cell);



您是否将图像直接添加到 pdf 文档(表外)只是为了比较/仔细检查图像尺寸?

document.add(image);



我假设您希望图像在单元格中居中,并在其周围留出一些空间。作为最后的手段,你可以改变你的形象。将其设为具有透明背景的 png,并确保图像的所有边缘周围都有一些透明的“边距”。

编辑

我刚刚下载了 v5.0.2,得到的结果与上述相同。我已经尝试过使用比单元格大小更小和更大的图像,并且行为是相同的;第一种方法缩放图像,第二种方法没有。

编辑

嗯,很明显,多年来我对图像的整个 DPI 问题一直是错误的。我似乎看不出图像的 DPI 有什么不同。
我以三种不同的分辨率(72dpi、96 dpi 和 110 dpi)创建了一个 600x400 像素的图像。然后我将这些图像中的每一个都添加到一个正好为 600x400 的新文档中。

Dim pSize As Rectangle = New Rectangle(600, 1000)
Dim document As Document = New Document(pSize, 0, 0, 0, 0)

对于三个图像文件中的每一个,当使用

添加到文档时
document.add(image)

它们与文档完美契合,不同 DPI 设置没有差异。

【讨论】:

  • 我试过 PdfPCell cell = new PdfPCell(image);和 doc.Add(image); (直接到文档添加)并且它们给出相同大小的结果。是否可能与 DPI 有关?
  • 是的。很多图像,例如在 Paint.NET 中显示的图像,都是 96 dpi(或其他)。 iTextSharp 始终使用 72 dpi。我确实知道,如果您的图像的 dpi 不同于 72,您可能会得到不同的结果。我忘记了这一点,因为我总是以 72dpi 创建“用于 pdf”图像。
  • 72?在接受的答案中说这里是 110:*.com/questions/2752789/… 还是我误解了这个答案?
  • 我不知道了...无论我尝试什么都对我不起作用...任何机会我都可以将解决方案和图像发送给您,以便您可以尝试?我完全被这个难住了......
【解决方案2】:

@Stewbob 的回答确实有效,但只是偶然与表的方法有关。

iTextSharp 的特点是它的行为会根据您使用的构造函数而有所不同。这将(令人讨厌)放大图像以填充单元格:

PdfPCell c = new PdfPCell();
c.Add(image);
c.setHorizontalAlignment(Element.ALIGN_CENTER); // this will be ignored

但这会使图像保持您设置的大小(并允许对齐):

PdfPCell c = new PdfPCell(image);  
c.setHorizontalAlignment(Element.ALIGN_CENTER);

我不知道这是为什么,如果您在构造函数中添加图像,则与单元格处于“文本模式”有关,如果稍后添加,则与“复合模式”有关(在这种情况下,每个对象应该照顾它自己的对齐方式)。

更多信息(在 Java 中,但仍然适用)http://tutorials.jenkov.com/java-itext/table.html#cell-modes

【讨论】:

  • 这可能是我见过的最奇怪的功能而不是错误。非常感谢
  • 赞成这个答案,因为它让我找到了解决同样问题的方法。但是我遇到了一个完全不同的行为 - AddElement 方法将图像保留为您设置的大小,但构造函数会调整图像的大小。我正在使用 iTextSharp 5.5.3.0。
【解决方案3】:

因此,如果您必须保持 PdfPCell 中图像的大小,您可以查看以下代码:

                iTextSharp.text.Image image = iTextSharp.text.Image.GetInstance(imageFilePath);

                 // Save the image width
                float width = image.Width;
                PdfPCell cell = new PdfPCell();
                cell.AddElement(image);


                // Now find the Image element in the cell and resize it
                foreach (IElement element in cell.CompositeElements)
                {
                    // The inserted image is stored in a PdfPTable, so when you find 
                    // the table element just set the table width with the image width, and lock it.
                    PdfPTable tblImg = element as PdfPTable;
                    if (tblImg != null)
                    {
                        tblImg.TotalWidth = width;
                        tblImg.LockedWidth = true;
                    }
                }

【讨论】:

    【解决方案4】:

    该函数具有适合图像的属性。只添加一个 true

    cell.AddElement(image,true);
    

    【讨论】:

    • 您使用哪个版本的 itextsharp 或什么类型的变量“单元格”?在我的(类型 PdfPCell)中,我只能找到方法:AddElement(IElement element)
    • 我也没有这种重载 - 使用 iTextSharp 5.5.9。
    【解决方案5】:

    对于那些要求超载的人,使用这个:

    var imageCell = new PdfPCell(image, true);
    

    而不是:

    cell.AddElement(image,true);
    

    【讨论】: