не удается найти все поля pdf (acroform)

#pdfbox

#pdfbox

Вопрос:

Учитывая этот PDF

С помощью этого кода я извлекаю все поля, но получаю половину из них:

 pdfOriginal.getDocumentCatalog().getAcroForm().getFields().forEach(field -> {
  System.out.println(field.getValueAsString());
});
  

Что здесь не так? Кажется, что все аннотации отсутствуют в ссылке aocroform, как правильно добавить аннотацию поля формы в объект acroform?

Обновление 1

Странная вещь здесь, если бы я попытался установить значение поля, на которое нет ссылок / найдено в getAcroForm.getFields() вот так :

 doc.getDocumentCatalog().getAcroForm().getField("fieldNotInGetFields").setValue("a");
  

Это работает

Обновление 2

Кажется, что с помощью doc.getDocumentCatalog().getAcroForm().getFieldTree() извлекаются все поля. Я не понимаю, почему doc.getDocumentCatalog().getAcroForm().getFields() нет?

Как правильно получить все поля PDF acroform.getFieldTree() или acroform.getFields() (мне нужно получить их, чтобы установить им частичное значение)

Комментарии:

1. Пожалуйста, прочитайте javadoc из двух, это объясняет это.

2. уже делал это, для меня это было вне поля зрения, но после нескольких попыток кода мне теперь ясно! большое вам спасибо @TilmanHausherr, позвольте мне ответить на мой вопрос небольшим примером кода или вы предпочитаете удалить его?

3. Пожалуйста, ответьте сами 🙂

4. Если есть что-то, что, по вашему мнению, следует добавить в javadoc, пожалуйста, укажите это.

5. javadoc кажется ясным, здесь не может быть лучше ^^ была моя ошибка

Ответ №1:

Из документа Java о методе public List<PDField> getFields() мы можем прочитать:

Поле может иметь дочерние элементы, которые являются полями (нетерминальное поле), или не иметь дочерних элементов, которые являются полями (поля терминала).

В моем случае некоторые поля содержат нетерминальное поле, поэтому, чтобы распечатать их все, нам нужно проверить, находимся ли мы в PDNonTerminalField подобном :

 document.getDocumentCatalog().getAcroForm().getFields().forEach(f -> {
    listFields(f);              
});

// loop over PDNonTerminalField otherwise print field value
public static void listFields(PDField f){
    if(f instanceof PDNonTerminalField) {
        ((PDNonTerminalField) f).getChildren().forEach(ntf-> {
            listFields(ntf);
        });         
    }else {
        System.out.println(f.getValueAsString());
    }
}