Skip to content

Support open-ended page ranges for graphical bounding boxes (page 0 = all pages, negative = from page N onward) #326

Description

@jzonthemtn

Summary

Graphical bounding boxes (policy.graphical.boundingBoxes) currently apply to a single, exact 1-based page. This proposes two open-ended page values so one box can span pages without knowing the document length up front:

  • 0 — the box covers every page.
  • -N — the box covers page N through the last page (so -2 is "all but the first page", e.g. a logo or footer on every page except the cover).

Any positive value keeps meaning the exact page, as today.

Motivation

Fixed regions are ideal for logos, watermarks, stamps, and letterhead that sit in the same spot on every page. Without an "all pages" (or "from page N onward") option, a caller has to know the page count and emit one box per page. These sentinels let a single box cover the whole document (or a tail of it) with no page-count knowledge.

Reference implementation (phileas-dotnet)

This is already implemented in phileas-dotnet so the two engines can match. The change is entirely in how PdfRedactor decides whether a box applies to a page:

internal static bool BoxAppliesToPage(BoundingBox box, int pageNumber) => box.Page switch
{
    0   => true,                     // all pages
    < 0 => pageNumber >= -box.Page,  // from page N to the last page
    _   => box.Page == pageNumber    // an exact page
};

This is used in place of the old boundingBoxes.Where(b => b.Page == pageNumber) filter when painting each page. The BoundingBox.page documentation was updated to describe the 0 / -N convention.

Proposed Java change

  • In the PDF redactor, replace the exact box.getPage() == pageNumber match with the equivalent predicate (0 → all pages, negative → from |page| to the last page, otherwise the exact page).
  • Document the page field convention on the bounding-box model.
  • No schema/type change is required — page is already an integer.

Acceptance criteria

  • An exact page value still matches only that page.
  • page = 0 covers every page of a multi-page PDF.
  • page = -N covers pages N through the last page (and -2 excludes the first page).
  • Unit tests for the page-matching predicate, plus an end-to-end test confirming an all-pages box redacts every page.

Notes

This keeps phileas (Java) and phileas-dotnet in sync. phileas-dotnet is a port of this engine and currently diverges on this behavior.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions