Břetislav Černík created PDFBOX-5686:
----------------------------------------

             Summary: Acroform international (czech) characters can't be 
written to the textfields
                 Key: PDFBOX-5686
                 URL: https://issues.apache.org/jira/browse/PDFBOX-5686
             Project: PDFBox
          Issue Type: Bug
          Components: AcroForm
    Affects Versions: 3.0.0 PDFBox
         Environment: Windows 11,  JDK 14
            Reporter: Břetislav Černík


I try use the ImportXFDF.java but it does not work for the czech characters in 
the xfdf file.

The error is

Exception in thread "main" java.lang.IllegalArgumentException: U+0159 is not 
available in this font's encoding: WinAnsiEncoding
    at 
org.apache.pdfbox.pdmodel.font.PDTrueTypeFont.encode(PDTrueTypeFont.java:404)
    at org.apache.pdfbox.pdmodel.font.PDFont.encode(PDFont.java:337)
    at org.apache.pdfbox.pdmodel.font.PDFont.getStringWidth(PDFont.java:368)
    at 
org.apache.pdfbox.pdmodel.interactive.form.PlainText$Paragraph.getLines(PlainText.java:178)
    at 
org.apache.pdfbox.pdmodel.interactive.form.PlainTextFormatter.format(PlainTextFormatter.java:182)
    at 
org.apache.pdfbox.pdmodel.interactive.form.AppearanceGeneratorHelper.insertGeneratedAppearance(AppearanceGeneratorHelper.java:609)
    at 
org.apache.pdfbox.pdmodel.interactive.form.AppearanceGeneratorHelper.setAppearanceContent(AppearanceGeneratorHelper.java:443)
    at 
org.apache.pdfbox.pdmodel.interactive.form.AppearanceGeneratorHelper.setAppearanceValue(AppearanceGeneratorHelper.java:259)
    at 
org.apache.pdfbox.pdmodel.interactive.form.PDTextField.constructAppearances(PDTextField.java:262)
    at 
org.apache.pdfbox.pdmodel.interactive.form.PDTerminalField.applyChange(PDTerminalField.java:209)
    at 
org.apache.pdfbox.pdmodel.interactive.form.PDTextField.setValue(PDTextField.java:218)
    at formpdf.ImportXFDF.lambda$setFont$0(ImportXFDF.java:194)
    at java.base/java.util.Iterator.forEachRemaining(Iterator.java:133)
    at formpdf.ImportXFDF.setFont(ImportXFDF.java:178)
    at formpdf.ImportXFDF.importXFDF(ImportXFDF.java:137)
    at Test.TestFormPDF(Test.java:23)
    at Test.main(Test.java:18)

 

I try to set the TTF Unicode font for every textfields but the same error is 
generated.

There are test code from modified ImportXFDF. I use the method importXFDF

package formpdf;

//import com.sun.xml.internal.ws.policy.privateutil.PolicyUtils;
import java.io.BufferedOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.OutputStreamWriter;
import java.io.UncheckedIOException;
import java.io.File;

import java.util.Iterator;

import static org.apache.pdfbox.cos.COSName.Off;

import org.apache.pdfbox.cos.COSName;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.PDDocumentCatalog;
import org.apache.pdfbox.pdmodel.PDResources;
import org.apache.pdfbox.pdmodel.fdf.FDFDocument;
import org.apache.pdfbox.pdmodel.interactive.form.PDAcroForm;
import org.apache.pdfbox.pdmodel.interactive.form.PDCheckBox;
import org.apache.pdfbox.pdmodel.interactive.form.PDComboBox;
import org.apache.pdfbox.pdmodel.interactive.form.PDField;
import org.apache.pdfbox.pdmodel.interactive.form.PDListBox;
import org.apache.pdfbox.pdmodel.interactive.form.PDRadioButton;
import org.apache.pdfbox.pdmodel.interactive.form.PDTextField;
import org.apache.pdfbox.Loader;
import org.apache.pdfbox.pdmodel.font.PDFont;
import org.apache.pdfbox.pdmodel.font.PDType0Font;
import org.apache.pdfbox.pdmodel.font.PDTrueTypeFont;
import org.apache.pdfbox.pdmodel.font.encoding.Encoding;
import org.apache.pdfbox.pdmodel.font.encoding.StandardEncoding;
import org.apache.pdfbox.pdmodel.font.encoding.WinAnsiEncoding;
import org.apache.pdfbox.pdmodel.font.encoding.GlyphList;
import org.apache.pdfbox.cos.COSBase;
import org.apache.pdfbox.cos.COSName;
import org.apache.fontbox.ttf.TrueTypeFont;

public class ImportXFDF 
{

   /**
    * @param ac_PDFDocument
    * @param ac_XFDFData
    * @param ac_PDFResult
    * @param ab_clearFields
    * @throws IOException
    */
   public static void importXFDF
   (
      InputStream ac_PDFDocument, 
      InputStream ac_XFDFData, 
      OutputStream ac_PDFResult, 
      boolean ab_clearFields,
      boolean ab_RemoveFields
   ) throws IOException
    {
        PDDocument 
           lc_PDDDocument = null;
         String   ls_FontName = "ArialMT";
//         MyEncoding
//            lc_Encoding;
//         lc_Encoding = new MyEncoding();
//         lc_Encoding.addChar( 0x0159, "rcaron" );
         try 
         {
            lc_PDDDocument = Loader.loadPDF( ac_PDFDocument.readAllBytes() ); 
//PDDocument.load( ac_PDFDocument);
   
         }
         catch (IOException  ex) 
         {
            throw new IOException("Error while reading pdf", ex);
         }
   
   
         FDFDocument fdfDocument = null;
         try 
         {
   //            fdfDocument =  FDFDocument.loadXFDF( ac_XFDFData);
           fdfDocument =  Loader.loadXFDF( ac_XFDFData);
         } 
         catch (IOException ex)
         {
            throw new IOException("Error while reading xfdf file", ex);
         }
         PDDocumentCatalog docCatalog = lc_PDDDocument.getDocumentCatalog();
         PDAcroForm acroForm = docCatalog.getAcroForm();
         if(acroForm == null){
            throw new IOException("Internal Error with acroform");
         }
         PDResources formResources = acroForm.getDefaultResources();
//         PDTrueTypeFont lc_Arial = (PDTrueTypeFont) 
formResources.getFont(COSName.getPDFName( "Arial" ));
//         TrueTypeFont   lc_ArialTTF = lc_Arial.getTrueTypeFont();
//         PDFont lc_ArialNew = PDType0Font.load( lc_PDDDocument, lc_ArialTTF, 
true);
//         lc_ArialTTF.close();
       
//        PDFont lc_Arial = PDTrueTypeFont.load( lc_PDDDocument, new 
File("C:\\Windows\\Fonts\\arial.ttf"),lc_Encoding );
         PDFont lc_Arial = PDType0Font.load( lc_PDDDocument, new 
File("C:\\Windows\\Fonts\\arial.ttf") );
//         lc_Arial.addToSubset( 0x0159 );
//         lc_Arial.subset();
//        PDFont lc_ArialB = PDTrueTypeFont.load( lc_PDDDocument, new 
File("C:\\Windows\\Fonts\\arialbd.ttf"), lc_Encoding );
//       PDFont lc_CourNB = PDTrueTypeFont.load( lc_PDDDocument, new 
File("C:\\Windows\\Fonts\\courbd.ttf"), lc_Encoding );

//         formResources.put( COSName.getPDFName( ls_FontName ), lc_ArialNew );
        ls_FontName = formResources.add(lc_Arial).getName();
         System.out.println( ls_FontName );
//       formResources.add(lc_ArialB);
//       formResources.add(lc_CourNB);
         System.out.println( formResources.getFontNames());
         acroForm.setDefaultAppearance( String.format("/%s 0 Tf 0 g", 
ls_FontName  ));
//        PDFont lc_font = PDType0Font.load(lc_PDDDocument, new 
File("C://Windows/Fonts/arial.ttf"));
//        formResources.put(COSName.getPDFName("Arial"), lc_font);
//        formResources.add(lc_font);
//        System.out.println( formResources.getFontNames());

//        acroForm.setDefaultResources(formResources);
//        acroForm.setDefaultAppearance("/Arial 0 Tf 0 g");
//        System.out.println( acroForm.getDefaultAppearance());


        acroForm.setCacheFields( true );

        if (ab_clearFields) {
            try 
            {
                ClearFileds(acroForm.getFieldIterator());
            } 
            catch (UncheckedIOException ex) 
            {
                throw new IOException("Error during clearing field forms", ex);
            }
        }
/*
*/
        acroForm.setNeedAppearances( true );
         setFont(acroForm.getFieldIterator(), ls_FontName );
        acroForm.setNeedAppearances( true );
        try 
        {

            acroForm.importFDF(fdfDocument);
        } 
        catch (IOException ex)
        {
            throw new IOException("Error while importing data", ex);
        }

       acroForm.setNeedAppearances(true);
        if ( ab_RemoveFields )
        {
           acroForm.setNeedAppearances(false);
           try
           {
              acroForm.refreshAppearances();
           }
           catch (IOException e )
           {
               throw new IOException( "Chyba při obnově vzhledu", e );
           }
         System.out.println( "Flatten" );
           acroForm.flatten();
        }
        // konec úpravy aby ukazoval správn? vzhled
        try
        {
            lc_PDDDocument.save(new BufferedOutputStream( ac_PDFResult ));
        } 
        catch(IOException ex)
        {
            throw new IOException("Error while saving to pdf", ex);
        }
    }

   private static void setFont(Iterator<PDField> ac_FieldIterator, String 
as_FontName ) throws UncheckedIOException
   {
     ac_FieldIterator.forEachRemaining
     (
        (field) ->
        {
            if (field instanceof PDTextField)
            {

//                    System.out.println(((PDTextField) 
field).getDefaultAppearance());
//                    ((PDTextField) field).setDefaultAppearance("/F19 0 Tf 0 
g");
                ((PDTextField)field).setDefaultAppearance( String.format("/%s 0 
Tf 0 g", as_FontName  ));
            System.out.println( field.getFullyQualifiedName() + ": " + 
((PDTextField)field).getDefaultAppearance() + " to " + String.format("/%s 10 Tf 
0 g", as_FontName  ) );

            try
            {
                  if (field.getFullyQualifiedName()=="PL_NAZEV" )
                  {}
               else
               ((PDTextField) field).setValue("\u0159" ); //Příliš žluťoučký 
kůň úpěl ďábelské ódy");
            }
            catch (IOException e)
            {
               throw new UncheckedIOException( e );
            }
         }
        }
     );
   }
    private static void ClearFileds(Iterator<PDField> ac_FieldIterator) throws 
UncheckedIOException
    {
      ac_FieldIterator.forEachRemaining
      (
         (field) ->
         {
            try {
                if (field instanceof PDCheckBox)
                {

                    ((PDCheckBox) field).unCheck();
                }
                else if (field instanceof PDComboBox)
                {
                    field.setValue(Off.getName());
                }
                else if (field instanceof PDListBox)
                {
                    field.setValue(Off.getName());
                }
                else if (field instanceof PDRadioButton)
                {
                    field.setValue(Off.getName());
                }
                else if (field instanceof PDTextField)
                {

//                    System.out.println(((PDTextField) 
field).getDefaultAppearance());
//                    ((PDTextField) field).setDefaultAppearance("/F19 0 Tf 0 
g");
                    field.setValue("");
                }
            } 
            catch (IOException ex )
            {
                throw new UncheckedIOException(ex);
            }
         }
      );
    }

   /**
    * @param ac_PDFDocument
    * @param ac_XFDFData
    * @throws IOException
    */
   public static void exportXFDF(InputStream ac_PDFDocument, OutputStream 
ac_XFDFData )
            throws IOException
    {
       OutputStreamWriter outputStreamWriter = new 
OutputStreamWriter(ac_XFDFData);
       PDDocumentCatalog lc_pdDocumentDocumentCatalog;
       PDDocument lc_pdDocument = null;
       PDAcroForm lc_acroForm;
        try {
//            lc_pdDocument = PDDocument.load(ac_PDFDocument);
           lc_pdDocument = Loader.loadPDF( ac_PDFDocument.readAllBytes());
        }
        catch (IOException  ex)
        {
            throw new IOException("Error while reading pdf", ex);
        }

      lc_pdDocumentDocumentCatalog = lc_pdDocument.getDocumentCatalog();
      lc_acroForm = lc_pdDocumentDocumentCatalog.getAcroForm();
      FDFDocument lc_fdfDocument = null;
        try {
            lc_fdfDocument = lc_acroForm.exportFDF();
        }catch(IOException ex){
            throw new IOException("Error while exporting fdf", ex);
        }
        try{
            lc_fdfDocument.saveXFDF(outputStreamWriter);
        } catch (IOException ex){
            throw new IOException("Error during saving XFDF",ex);
        }
    }

}

 

The acroForm.setNeedAppearances( true ) is not usable for the final output. 
It is not suported in the some viewers I.e. apple tablets

Best regards

 Břetislav Černík
 [email protected]



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to