使用iTextSharp填写其他字段时,如何强制PDF格式化和计算?

我有一个包含许多文本字段的PDF表单 . 在这些字段中输入的值用于计算其他字段中的值(计算字段是只读的) .

当我在Adobe Reader中打开表单并填写字段时,计算字段会自动重新计算 .

但是,我使用iTextSharp填充字段,展平生成的表单,然后通过Web将展平的表单流回用户 .

该部分工作正常,但计算字段永远不会计算 . 我假设因为没有用户触发事件(如keydowns或焦点或模糊)正在触发,所以不会发生计算 .

显然,我可以从可填写的表单中删除计算,并在填充字段时在服务器上完成所有计算,但我希望可填写的表单可供人类和服务器使用 .

有谁知道如何强制计算?

编辑:我感觉不是太多iText / iTextSharp在这里爱...

这里有一些细节 . 将stamper.AcroFields.GenerateAppearances设置为true无济于事 .

我认为答案在于页面操作中的某个地方,但我不知道如何触发它...

回答(5)

2 years ago

Paulo Soares(iText的主要开发者之一和iTextSharp的当前维护者)says

iText不会为修复计算字段做任何努力,因为大部分时间都是不可能的 . PdfCopyFields有一些支持,有时可以工作,有时不工作 .

2 years ago

我已经想出了如何做到这一点 . 有关stackoverflow问题,请参阅我的答案:

How to refresh Formatting on Non-Calculated field and refresh Calculated fields in Fillable PDF form

2 years ago

我通过调用Doc对象上的javascript方法calculateNow更新了我的pdf的所有计算字段 .

根据adobe javascript文档 this.calculateNow();

强制计算当前文档中的所有计算字段 . 当表单包含许多计算时,在用户将数据输入字段后,即使它不是计算字段,也会有明显的延迟 . 一种策略是在某个时刻关闭计算并稍后再打开它们(参见示例) .

要使用iTextSharp包含javascript调用:

using (PdfReader pdfReader = new PdfReader(pdfTemplate))
using (PdfStamper pdfStamper = new PdfStamper(pdfReader, new FileStream(newFile, FileMode.Create)))
{
    // fill f1 field and more...
    AcroFields pdfFormFields = pdfStamper.AcroFields;
    pdfFormFields.SetField("f1", "100");
    //...

    // add javascript on load event of the pdf
    pdfStamper.JavaScript = "this.calculateNow();";
    pdfStamper.Close();
}

2 years ago

在服务器端,查看计算字段中是否有答案 . 如果没有,请计算它们 .

2 years ago

正如Greg Hurlman所说,你应该自己在服务器上进行计算 . 这不仅仅是为了方便,实际上还有很好的理由 .

客户拥有的任何文件,都有可能与之相关 . 我不知道PDF格式的用途是什么,但它有可能以某种方式与金钱相关联,因此人们通过使计算显示错误的结果而作弊的可能性 . 如果您信任在客户端进行的计算,则无法检测到它 .

当您从客户端收到PDF表单时,您应该重做所有计算,以便您知道它们是正确的 . 然后,如果您还要比较客户端的版本,您应该检查它们是否已经被搞砸了 .

不要以为你的客户不值得信任吗?对你有好处,但证据不同意 . 我最早的编程介绍之一是为SimCity打开存档以给自己更多的钱 . 如果有机会以某种方式作弊,那么在某些时候人们会尝试 .