在使用 itextsharp 创建的 PDF table 中设置单元格高度

Set cell height in PDF table created with itextsharp

我使用以下代码在我的 itextsharp PDF 文档中创建了一个 table:

foreach (var subComp in competency.SubCompetensies)
{
    cell = new PdfPCell(new Phrase(0, subComp.DescriptionMin, _nfDescr));
    cell.Padding = 5;
    cell.Rowspan = 2;

    table.AddCell(cell);

    cell = new PdfPCell(new Phrase(0, subComp.Name, _nfSubComp));
    cell.Colspan = 10;
    cell.Padding = 5;
    table.AddCell(cell);

    cell = new PdfPCell(new Phrase(subComp.DescriptionMax, _nfDescr));
    cell.Padding = 5;
    cell.Rowspan = 2;

    table.AddCell(cell);

    for (int i = 1; i < 11; i++)
    {
        cell = new PdfPCell(new Phrase(0, i.ToString(), _nfScale));
        cell.FixedHeight = 15f;
        cell.Padding = 3;
        cell.PaddingLeft = 5;
        table.AddCell(cell);
    }
}

结果如下:

如您所见,每行带有数字的单元格的高度都不同。貌似cell.FixedHeight 属性被忽略了

有没有办法设置这些单元格的固定高度?

好吧,我找到了解决办法。至于我呢,好像有点小色狼,但是我的deadline根本不在乎我的代码有多精致

可能有人会发现它有用。

为什么 FixedHeight 被忽略了?

因为最后抽出数字的单元格连续消耗了所有空闲space。

可能的解决方案

我只能看到两种方式:

  • 显然,改变一行中单元格的顺序
  • 自己渲染行的中心部分

我决定选择第二种方式。 我没有使用 rowspans/colspans 创建十个单元格并将它们添加到一行,而是只添加了三个单元格:

 cell = new PdfPCell(new Phrase(0, subComp.DescriptionMin, _nfDescr));
                            cell.MinimumHeight = 50;
                            cell.Padding = 5;
                            cell.BorderColor = BaseColor.WHITE;
                            cell.BackgroundColor = new BaseColor(233, 240, 242);
                            table.AddCell(cell);

                            cell = new PdfPCell();
                            cell.CellEvent = new CellEvents(subComp);
                            cell.BorderColor = BaseColor.WHITE;
                            table.AddCell(cell);

                            cell = new PdfPCell(new Phrase(subComp.DescriptionMax, _nfDescr));
                            cell.Padding = 5;
                            cell.BorderColor = BaseColor.WHITE;
                            cell.BackgroundColor = new BaseColor(233, 240, 242);
                            table.AddCell(cell);

我将自定义单元格事件添加到第二次销售。它在设置单元格高度之后和布局渲染之前触发。这是事件处理程序的代码:

 private class CellEvents : IPdfPCellEvent
{
    public void CellLayout(PdfPCell cell, Rectangle position, PdfContentByte[] canvases)
    {

        int scoreCellHeight = 20;

        var pdfContentByte = canvases[0];
        pdfContentByte.SaveState();

        pdfContentByte.Rectangle(pos.Left, pos.Bottom + scoreCellHeight, pos.Width, pos.Height - scoreCellHeight);
        pdfContentByte.SetColorFill(new BaseColor(233, 240, 242));
        pdfContentByte.Fill();


        ColumnText ct = new ColumnText(pdfContentByte);
        ct.SetSimpleColumn(new Phrase(_model.Name, _nfSubComp), pos.Left, pos.Bottom + 20, pos.Left + pos.Width, pos.Bottom + pos.Height - 5, 10, Element.ALIGN_CENTER);
        ct.Go();

        float scaleWidth = pos.Width / 10;

        for (int i = 1; i < 11; i++)
        {
            float scaleLeft = pos.Left + (i - 1) * pos.Width / 10;

            pdfContentByte.Rectangle(scaleLeft, pos.Bottom, scaleWidth, scoreCellHeight);

            pdfContentByte.SetColorFill(i % 2 == 1
                ? new BaseColor(Color.LightBlue)
                : new BaseColor(233, 240, 242));
            pdfContentByte.Fill();


            ct.SetSimpleColumn(new Phrase(i.ToString(), _nfScale), scaleLeft, pos.Bottom,
                    scaleLeft + scaleWidth, pos.Bottom + 7, 0, Element.ALIGN_CENTER);
            ct.Go();
        }
        canvases[0].RestoreState();
    }
}

我跳过了一些细节,例如 class 构造函数和绘制标记(屏幕截图中的红色数字)的代码。

结果:

我想,这个解决方法不是最优的。但是我必须绘制一个红色标记,所以无论如何我都必须处理单元格渲染事件。

希望有人能给出正确的解决方案。