We're sorry Aspose doesn't work properply without JavaScript enabled.

Free Support Forum - aspose.com

NullPointer using LayoutEnumerator in HeaderFooter Section

Hi, I would like to ensure the correct anchor for any shape in my document so I introduced below implementation:

    static void ensureCorrectAnchorTest() throws Exception {
        Document doc = new Document();
        License lic = new License();
        lic.setLicense(System.getProperty("user.dir") + "/src/main/resources/Aspose.Words.Java.lic");

        doc.removeAllChildren();
        Section section = new Section(doc);
        doc.appendChild(section);
        DocumentBuilder builder = new DocumentBuilder(doc);

        /* Create shape in usually section*/
        double yShapePosition = 200;
        Shape box2 = new Shape(doc, ShapeType.TEXT_BOX);
        box2.setWidth(100);
        box2.setHeight(70);
        box2.setWrapType(WrapType.NONE);
        box2.setTop(yShapePosition);
        box2.setLeft(100);
        box2.setRelativeHorizontalPosition(RelativeHorizontalPosition.PAGE);
        box2.setRelativeVerticalPosition(RelativeVerticalPosition.PAGE);
        box2.setFillColor(Color.BLUE);
        ensureCorrectAnchorPosition(builder, yShapePosition);
        builder.insertNode(box2);

        /* Create shape in header-footer section*/
        final Section currentSection = builder.getCurrentSection();
        PageSetup pageSetup = currentSection.getPageSetup();
        pageSetup.setDifferentFirstPageHeaderFooter(true);
        pageSetup.setOddAndEvenPagesHeaderFooter(true);


        builder.moveToHeaderFooter(HeaderFooterType.HEADER_FIRST);
        builder.writeln("Test");
        double yPosition = 400;


        Shape headerBox = new Shape(doc, ShapeType.TEXT_BOX);
        headerBox.setWidth(50);
        headerBox.setHeight(50);
        headerBox.setWrapType(WrapType.NONE);
        headerBox.setTop(yPosition);
        headerBox.setLeft(100);
        headerBox.setRelativeHorizontalPosition(RelativeHorizontalPosition.PAGE);
        headerBox.setRelativeVerticalPosition(RelativeVerticalPosition.PAGE);
        headerBox.setFillColor(Color.RED);
        ensureCorrectAnchorPosition(builder, yShapePosition);
        builder.insertNode(headerBox);


        OoxmlSaveOptions options = new OoxmlSaveOptions();
        options.setCompliance(OoxmlCompliance.ISO_29500_2008_STRICT);
        builder.getDocument()
                .save(System.getProperty("user.dir") + File.separator + "anhor_test_" + System.currentTimeMillis() + ".docx", options);
    }

    static void ensureCorrectAnchorPosition(final DocumentBuilder builder, final double yShapePosition) {

        Paragraph currentParagraph = builder.getCurrentParagraph();
        Paragraph targetAnchorParagraph = currentParagraph;
        final Section parentSection = currentParagraph.getParentSection();
        final ParagraphCollection paragraphs = parentSection.getBody().getParagraphs();
        final Paragraph[] paragraphsArray = paragraphs.toArray();
        int i = findCurrentParagraphArrayIndex(paragraphsArray, currentParagraph);

        try {
            LayoutCollector collector = new LayoutCollector(builder.getDocument());
            LayoutEnumerator enumerator = new LayoutEnumerator(builder.getDocument());
            enumerator.setCurrent(collector.getEntity(currentParagraph));

            if (enumerator.getRectangle().getY() < yShapePosition) {
                targetAnchorParagraph = findInNextParagraphs(enumerator, paragraphsArray, collector, builder, i, yShapePosition);
            } else if (enumerator.getRectangle().getY() > yShapePosition) {
                targetAnchorParagraph = findInPreviousParagraphs(enumerator, paragraphsArray, collector, i, yShapePosition);
            }
        } catch (Exception e) {
            e.printStackTrace();
            builder.moveTo(builder.getCurrentParagraph());
        }
        builder.moveTo(targetAnchorParagraph);
    }


    static private int findCurrentParagraphArrayIndex(final Paragraph[] paragraphsArray,
                                               final Paragraph currentParagraph) {
        for (int j = 0; j < paragraphsArray.length; j++) {
            if (paragraphsArray[j].equals(currentParagraph)) return j;
        }
        return -1;
    }

    static private Paragraph findInNextParagraphs(final LayoutEnumerator enumerator,
                                           final Paragraph[] paragraphsArray,
                                           final LayoutCollector collector,
                                           final DocumentBuilder builder,
                                           final int currentParagraphIndex,
                                           final double yShapePosition) throws Exception {
        for (int j = currentParagraphIndex + 1; j < paragraphsArray.length; j++) {
            enumerator.setCurrent(collector.getEntity(paragraphsArray[j]));
            if (enumerator.getRectangle().getY() >= yShapePosition) {
                return paragraphsArray[j];
            }
        }
        return createNearestParagraphToShape(builder, enumerator, paragraphsArray[paragraphsArray.length - 1], yShapePosition);
    }

    static private Paragraph findInPreviousParagraphs(final LayoutEnumerator enumerator,
                                               final Paragraph[] paragraphsArray,
                                               final LayoutCollector collector,
                                               final int currentParagraphIndex,
                                               final double yShapePosition) throws Exception {
        for (int j = currentParagraphIndex - 1; j > 0; j--) {
            enumerator.setCurrent(collector.getEntity(paragraphsArray[j]));
            if (enumerator.getRectangle().getY() <= yShapePosition) {
                return paragraphsArray[j];
            }
        }
        return paragraphsArray[0];
    }

    static private Paragraph createNearestParagraphToShape(final DocumentBuilder builder,
                                                    final LayoutEnumerator enumerator,
                                                    final Paragraph lastParagraphOnPage,
                                                    final double yShapePosition) throws Exception {
        builder.moveTo(lastParagraphOnPage);
        Paragraph currentParagraph = null;
        while (enumerator.getRectangle().getY() < yShapePosition) {
            currentParagraph = builder.insertParagraph();
            enumerator.setCurrent(new LayoutCollector(builder.getDocument()).getEntity(currentParagraph));
        }
        return currentParagraph;
    }

As a result in the normal section, any shape is placed correctly ( next to closest paragraph), but in the case when I want to achieve the same result in HeaderFooter section I get NullPointer.
@tahir.manzoor

@aolo23

Please move the cursor to the document’s body before using layout APIs to avoid this issue. You can move the cursor to the start of document as shown below.

static void ensureCorrectAnchorPosition(final DocumentBuilder builder, final double yShapePosition) throws Exception {

	builder.moveToDocumentStart();
    Paragraph currentParagraph = builder.getCurrentParagraph();
    Paragraph targetAnchorParagraph = currentParagraph;
    final Section parentSection = currentParagraph.getParentSection();
    final ParagraphCollection paragraphs = parentSection.getBody().getParagraphs();
    final Paragraph[] paragraphsArray = paragraphs.toArray();
    int i = findCurrentParagraphArrayIndex(paragraphsArray, currentParagraph);