Commit Graph
3415 Commits
Author SHA1 Message Date
FredApps d1fcc12e07 Integrate KenM76 PR #4943 2026-10-29 02:36:20 +01:00
FredApps ebd7578cc3 Integrate KenM76 PR #4913
# Conflicts:
#	crates/render/tests/it/main.rs
2026-10-29 02:36:20 +01:00
FredApps d9ddd8a8b0 Integrate KenM76 PR #4906 2026-10-29 02:35:58 +01:00
FredApps b0555cb918 Integrate KenM76 PR #4898
# Conflicts:
#	vendor/README.md
2026-10-29 02:35:58 +01:00
FredApps a66686cb0d Integrate KenM76 PR #4862 2026-10-29 02:34:57 +01:00
FredApps f716bd1462 Integrate KenM76 PR #4841
# Conflicts:
#	crates/automation/tests/it/main.rs
2026-10-29 02:34:57 +01:00
FredApps 2e6f7e5d3f Integrate KenM76 PR #4831 2026-10-29 02:34:41 +01:00
aiongg dc943eeb13 Merge pull request #4718 from alehel/fix/marks-update-preview-without-old-marks
fix(ui): Update previews the page without the marks it replaces
2026-10-28 17:59:41 -04:00
aiongg 7cde655cc2 Merge pull request #4709 from alehel/fix/page-cursor-writer
fix(ui): the page sets its cursor once, from the top claim the tool reaches
2026-10-28 17:57:29 -04:00
aiongg f824475202 Merge pull request #4631 from Lcoding15/fix/delete-one-radio-button
M6: Delete removes one selected radio button, not its whole group (#4609)
2026-10-28 17:55:17 -04:00
.CooCoo 222a124650 M5: Import comments takes another PDF and copies its comments onto the same pages (#4595)
* M5: Import comments takes another PDF and copies its comments onto the same pages

Import comments read only XFDF, FDF, XML, XDP, CSV and text data files.
It now also takes a PDF: each comment of that PDF is copied onto the
page with the same number, at the same place, with its appearance
stream, its pop-up, its replies and its layer. Comments on pages past
the document's last page are left out, together with replies to them.
Links, form fields and redaction marks are not copied. A comment named
like one already on its page replaces it, as an XFDF or FDF import
does. A PDF without comments is refused with "nothing in the file
matches this document", and a PDF that needs a password is refused.

- organize: import_comments copies the comments with the page copier
  that Insert Pages uses, and registers the layers they use.
- engine: Edit::ImportData reads a file that starts with %PDF- as a PDF.
  Any other file goes to the data importer first, and is read as a PDF
  when that fails, %PDF- occurs in its first 1,024 bytes and the PDF
  reader opens it.
- ui: Comments > Import comments lists .pdf files; form.import_data
  lists the same files as before.
- automation: the doc_import_data description names the PDF case.
- parity: comment.import-from-pdf is shipped.

* Import comments: an annotation that is no comment keeps its name

A comment imported from a PDF replaced any annotation of the same /NM
on its page that was not locked, a redaction mark or a widget, so a
link, screen or 3D annotation of that name was overwritten. Only an
annotation whose subtype is one of the copied comment subtypes is
replaced now; for any other, the copy is added beside it without the
name. The subtype is read through an indirect reference.

* Import comments: index each page's annotations instead of scanning them per comment

* Import comments: a layer that BaseState OFF hides stays hidden

* Import comments: a PDF with binary bytes before its header imports on an XFA form, and two comments with one name both land

On an XFA form, a decode failure no longer stops the import when a PDF
header is in the first 1,024 bytes; the PDF's comments are copied. Two
incoming comments on one page with the same /NM no longer replace the
same comment: the first replaces it, and the second is added without
the name.

* Import comments: an inline annotation on the page is replaced by name

An annotation written inline in a page's /Annots is made an indirect
object before names are matched, so an incoming comment with its /NM
replaces it instead of being added beside it.

* Import comments: two new comments with one name keep it once

When no comment on the page has the name, the first incoming comment
keeps its /NM and each later one with the same name is added without it.
2026-10-28 17:53:03 -04:00
aiongg 4d8dc3a1b7 Merge pull request #4560 from Lcoding15/feat/bookmarks-from-text-styles
M4: New bookmarks from text styles, for headings that aren't tagged (#1693)
2026-10-28 17:50:47 -04:00
.CooCoo 8f3a4f18bd M6: Organize pages ▸ Page properties sets the selected pages' tab order (#4516)
* M6: Organize pages ▸ Page properties sets the selected pages' tab order

Page properties in the Organize pages panel was listed as planned. In
the app, a page's tab order could only be set for every page at once,
with the form.tab_order commands, which offer no Unspecified. (The
form_tab_order tool already set chosen pages, Unspecified included.)

- Page properties (page.properties) opens a Tab Order dialog for the
  selected pages, with Use Row Order, Use Column Order, Use Document
  Structure and Unspecified. OK writes Edit::SetTabOrder for those pages
  as one undo step. The dialog opens on the pages' order, or with no
  choice made when they differ, and then OK is off until one is chosen.
  OK on the order the pages already have adds no undo step.
- Rows and columns run right to left in a document bound on the right,
  as Use Row Order and Use Column Order are described. PdfCraft reads a
  right-to-left binding from /ViewerPreferences /Direction /R2L
  (ISO 32000-1, 12.2, Table 150). Before, rank_tabs ranked them left to
  right.
- A page whose /Tabs is an indirect object now takes its row, column or
  structure order. Before, rank_tabs read only a direct name and ranked
  the page in annotation order.
- pdfcraft_forms::tab_orders and Document::tab_orders read each page's
  /Tabs. form_tab_order returns them as page_tabs, and reads without
  changing anything when it is given no order or field.
- set_option("dialog", "page-properties") opens the dialog.
- Parity: organize.page-tab-order is shipped, and its notes say the
  Actions tab of Page Properties (organize.page-actions) is still
  planned; the Organize pages grid notes list Page properties.

* Page properties: OK applies only to the document the dialog was opened on

The draft keeps the document's id. When another document is active by
OK, the dialog closes without changing either document.

* Menus: list Page properties… in the Pages menu

The menu bar now lists its commands explicitly, and every command with a menu group must appear in it.

* Page properties: apply the tab order only to an unchanged document

An edit, undo or redo made while the dialog is open can move the pages
at the stored indices. OK now closes the dialog without changing a page
when the document's edit generation differs from when it opened.

* Page properties: say when a document change cancels the tab order

OK shows a notice when the document changed or another document became
active while the dialog was open, so the user knows to open it again.
2026-10-28 17:48:29 -04:00
Eric Kaden 21f6c29d3e M6: form script messages keep their title, icon and buttons, and every one is shown (#4293, #4294) (#4306)
* M6: form script messages keep their title, icon and buttons, and every one is shown (#4293, #4294)

* M6: a form script message waits for a notice the toast already shows

* M6: form script messages past the queue's room are counted and reported

* M6: a sentence break in the merged parity note

* M6: an object that names no parameter is a message's text, as a String object or a caught error

* M6: the count of left-out script messages is said again if another notice replaces it before its time

* M6: a full stop between two sentences of the FormCalc parity note

* chore: re-run CI (a frame-budget timing test missed on a shared runner)
2026-10-28 17:46:11 -04:00
aiongg 31f51824c8 Merge pull request #2838 from jonathanwxh-cell/fix/cropbox-text-clipping
fix(render): clip extracted text to the page CropBox (#2670)
2026-10-28 17:43:51 -04:00
Lucas Sampaio Dias 03996b1025 Improve reading-colour preferences and add a settings shortcut (#2627)
* M3: improve reading-colour preferences and add settings shortcut

* M3: clarify the disabled reading-colour preview

* M3: adapt rebased preferences to current UI dependencies
2026-10-28 17:41:29 -04:00
oracola91 40c22e3ea5 Export Data as CSV keeps formula-like cells as text, like the merge report (#2524)
Export Data (CSV) wrote field names and values as they are, so a value
from a received form that starts with = or @ (or + or - when it is not a
number) runs as a formula when the CSV is opened in a spreadsheet.

It now uses the rule merge_csv got in #4101, moved unchanged into
runs_as_formula, so the merge report's output is the same. Import Data
takes the added ' off again, so Export Data then Import Data gives back
every value unchanged.
2026-10-28 17:39:06 -04:00
aiongg 750012c75f Merge pull request #2402 from wstock/fix/2368-flatten-no-rotate
Issue #2368: flattening keeps a NoRotate widget upright on a rotated page
2026-10-28 17:36:43 -04:00
Dylan M. Taylor 7555be3c7e Honor CARGO_BUILD_TARGET in FreeBSD packaging for aarch64 release builds (#5205)
The script already validated CARGO_BUILD_TARGET and named the archive after the arch, but
cargo build ignored it, so a cross build compiled for the host. Pass --target, resolve
host-tuple to the build host's triple first, and skip the --version smoke run for any
CARGO_BUILD_TARGET build (an aarch64 binary cannot run on the x86_64 VM).
2026-10-28 15:48:56 -04:00
Dylan M. Taylor 67d4f18179 Grant network access so update checks can reach GitHub (#5189) 2026-10-28 13:17:18 -04:00
Brandon ThomasandClaude Opus 5.5 75360d1d7d Release 0.15.0
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
v0.15.0
2026-10-28 12:09:26 -04:00
Brandon ThomasandClaude Opus 5.5 45d95f1107 macOS packaging: retry stapler when Apple's CloudKit drops the connection
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-28 12:09:18 -04:00
alehelandClaude Opus 5.5 1e239b0287 fix(ui): a page that fails to render ahead isn't asked again every frame
An error from rendering a neighbour ahead left it wanted and unqueued, so
each frame queued it again. It is now kept out of rendering ahead at that
scale (drawing it when shown still decides). On the web, where nothing
renders ahead, no render pool is made; picture()'s doc says a page that
fails keeps a picture drawn earlier.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-28 13:29:11 +01:00
alehelandClaude Opus 5.5 dcec1cecff fix(ui): Update's preview parses its unmarked copy once and keeps a page's failure to itself
The page shown was drawn through a fresh renderer each time, which parsed
the whole unmarked document on the UI thread; UnmarkedPages now parses it
once and keeps it. An error from rendering a page ahead (the pool retiring
its parser, a cancelled request) no longer marks that page failed: only
drawing it when shown decides, and a page that has a picture keeps it. On
the web, where the pool renders on the UI thread, nothing renders ahead.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-28 13:00:34 +01:00
alehelandClaude Opus 5.5 098a1f8321 fix(ui): Update draws the page shown without its marks at once, and a page that fails alone
The preview showed the page's thumbnail, old marks and all, until the
unmarked page rendered, and one page that failed to render switched the
unmarked preview off for every page. The page shown is now drawn from the
unmarked document straight away at the preview's size; the pages a step
goes to render ahead off the UI thread; a page that fails falls back to
its own thumbnail while the others keep theirs.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-28 12:40:45 +01:00
alehelandClaude Opus 5.5 1e01497649 fix(ui): Update prepares the unmarked pages once, and shows the thumbnail while one renders
The preview cloned and wrote the whole document on the UI thread for every
page it stepped to, and showed a blank sheet while the page rendered.
Document::without_marks now removes the marks of a kind from every page
once per dialog (UnmarkedPages), each page shown renders from it off the
UI thread, and the page's thumbnail stays until it arrives.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-28 12:09:37 +01:00
alehelandClaude Opus 5.5 c14910b182 docs(ui): a link's tip shows where a press acts on it, with Select or Link
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-28 11:55:53 +01:00
alehelandClaude Opus 5.5 871a3e1e96 Merge origin/main into fix/page-cursor-writer
main split canvas.rs, comments.rs, edit_text_ui.rs and moved the page
modules under canvas/ and tools/. The cursor claims are re-applied where
that code now lives:

- page_cursor.rs moves to canvas/, beside page_pointer.rs, re-exported
  from lib.rs the same way.
- canvas.rs: claims in the stamp, hand, text-cursor and link code;
  over_field and badge_hover are gone; the cursor is resolved once after
  the page loop in draw_pages. annotation_hover_text (canvas/area.rs) and
  its test give way to comments::describe and hover_tip.
- comments: describe, hover_tip and on_link go to tools/comments/input.rs,
  the hover_tip test to tools/comments/tests.rs.
- Edit text's picture claims go to tools/edit_text_ui/image.rs.
- The cursor guard test goes to canvas/page_pointer/tests.rs, with
  NOT_PAGE_CURSOR on main's paths.
- Tools that took ui only to set the cursor stop binding it.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-28 10:16:13 +01:00
alehelandClaude Opus 5.5 b3cbb77681 Merge origin/main into fix/marks-update-preview-without-old-marks
main split lib.rs: the unmarked_page field stays on PdfCraftApp in lib.rs,
its init and the render_pending check moved to app.rs.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-28 09:50:04 +01:00
jonathanwxh-cell fc010efe12 Merge remote-tracking branch 'upstream/main' into fix/cropbox-text-clipping 2026-10-28 16:17:07 +08:00
Claude 03fdf97cde Merge remote-tracking branch 'upstream/main' into feat/bookmarks-from-text-styles
# Conflicts:
#	crates/ui-egui/src/commands.rs
#	crates/ui-egui/src/dialogs.rs

Main split the command and dialog dispatch for its stricter clippy
rules; New bookmarks from text styles goes into the command list after
New bookmarks from structure, and its dialog into the dialog dispatch
next to the other dialogs with their own buttons.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01GbuSKAS2k5248LGFEapMUR
2026-10-28 06:07:14 +00:00
aiongg 20eebc1c33 deps: pin craft-libs at e11f9d9a so Cargo before 1.99 loads craft-menu (#5094)
craft-libs#366 drops the default-features override on craft-keymap that
older Cargo rejects. FreeBSD aarch64 builds with Rust 1.98.1 and failed
with "no matching package named craft-menu found" (craft-libs#364).
2026-10-27 22:16:40 -04:00
KenM76andClaude Opus 5.5 47909b04dd Merge origin/main into fix/text-matrix-survives-q
Upstream moved the interpreter state into a Walk struct; the saved-state
stack now carries (Gs, tm, tlm) there. Re-proved: the redact test fails
with upstream's interp.rs and passes with this one.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01SqmHYx8FiWM5PcsoiErgp9
2026-10-27 21:35:24 -04:00
Dylan M. Taylor 3932ee0639 Enforce Rust coding standards via Clippy (#4897)
* Refactor annot for strict Clippy checks

* Refactor automation for strict Clippy checks

* Refactor cos for strict Clippy checks

* Refactor edit for strict Clippy checks

* Refactor engine for strict Clippy checks

* Refactor export for strict Clippy checks

* Refactor forms for strict Clippy checks

* Refactor js for strict Clippy checks

* Refactor organize for strict Clippy checks

* Refactor pdfcraft-cli for strict Clippy checks

* Refactor preflight for strict Clippy checks

* Refactor print for strict Clippy checks

* Refactor redact for strict Clippy checks

* Refactor render for strict Clippy checks

* Refactor sign for strict Clippy checks

* Refactor ui canvas for strict Clippy checks

* Refactor ui commands for strict Clippy checks

* Refactor ui dialogs for strict Clippy checks

* Refactor ui support for strict Clippy checks

* Refactor ui tools for strict Clippy checks

* Refactor ui workflows for strict Clippy checks

* Refactor xfa for strict Clippy checks

* Refactor xfdf for strict Clippy checks

* Enforce workspace Clippy standards and document lint policy

* Fix menu overflow and form pointer handling

* Group annotation, form and document operation parameters

* Group signing and timestamp validation inputs

* Group demo form field properties

* Group UI interaction and rendering parameters

* Restore translated security and shortcut labels

* Fix platform-gated imports for Windows and wasm builds

* Qualify signing calls for macOS and Windows builds

* Restore the preflight check flow and the overflow menu title
2026-10-27 20:51:13 -04:00
Dylan M. Taylor e4966354ee Restore the preflight check flow and the overflow menu title 2026-10-28 00:21:28 +00:00
Dylan M. Taylor ad95afb0f8 Qualify signing calls for macOS and Windows builds 2026-10-28 00:21:27 +00:00
Dylan M. Taylor ef894ae6b8 Fix platform-gated imports for Windows and wasm builds 2026-10-28 00:14:57 +00:00
Dylan M. Taylor 76ce895478 Restore translated security and shortcut labels 2026-10-27 23:33:26 +00:00
Dylan M. Taylor 31833c992d Group UI interaction and rendering parameters 2026-10-27 23:25:40 +00:00
Dylan M. Taylor 775d6a4a19 Group demo form field properties 2026-10-27 23:25:40 +00:00
Dylan M. Taylor 5fecdb9cee Group signing and timestamp validation inputs 2026-10-27 23:25:40 +00:00
Dylan M. Taylor 81c63c037a Group annotation, form and document operation parameters 2026-10-27 23:25:39 +00:00
Dylan M. Taylor 63bc58a3d5 Fix menu overflow and form pointer handling 2026-10-27 23:16:56 +00:00
Dylan M. Taylor d95ff3898d Enforce workspace Clippy standards and document lint policy 2026-10-27 23:12:52 +00:00
Dylan M. Taylor 92bc2f9acd Refactor xfdf for strict Clippy checks 2026-10-27 23:12:52 +00:00
Dylan M. Taylor 9530dbb3e8 Refactor xfa for strict Clippy checks 2026-10-27 23:12:52 +00:00
Dylan M. Taylor 2ca92751cf Refactor ui workflows for strict Clippy checks 2026-10-27 23:12:52 +00:00
Dylan M. Taylor 21cae663d1 Refactor ui tools for strict Clippy checks 2026-10-27 23:12:52 +00:00
Dylan M. Taylor 2d27306a8d Refactor ui support for strict Clippy checks 2026-10-27 23:12:52 +00:00
Dylan M. Taylor bf89bf918c Refactor ui dialogs for strict Clippy checks 2026-10-27 23:12:52 +00:00