Commit Graph
908 Commits
Author SHA1 Message Date
aiongg 23da490a42 Merge table-cell-strokes: cell edge strokes in the Stroke panel and Cell Options, with gap colour and tint (#370)
Conflicts: ui-egui dialogs.rs (next's numberingSection arm and the branch's cellOptions arm; the branch's
copies of the dialog test helpers already on next dropped, its cell options test kept); idml tests.rs and
the i18n tables appended at the end on both sides (both kept; the branch's Gap Tint: and Tint: rows that
next already had dropped).
2026-10-10 20:30:54 +00:00
aiongg cce6f986c5 Tables: cell and table style strokes take type, gap colour and gap tint
style.cell.create/edit stroke and style.table.create/edit border use the
table.setCell stroke parser: type, gapColor (alias gapSwatch) and gapTint, with
the same validation. A bad value is an error and changes nothing.
2026-10-10 20:25:40 +00:00
aiongg 57d9761c69 Tables: cell strokes in the Stroke panel and Cell Options › Strokes and Fills
With cells selected, or the text cursor in a cell, the Stroke panel edits the
cell edges chosen on a drawn edge proxy: weight, type, colour, tint, gap colour
and gap tint. A click toggles a line, a double-click chooses all outer or all
inner lines, a triple-click chooses or clears all. Table › Cell Options ›
Strokes and Fills… has the same proxy and fields plus the cell fill colour and
tint, and applies the changed values in one undoable step. Translations for
the new strings in every interface language.
2026-10-10 20:16:53 +00:00
aiongg c1c44a3a2a Integration: German entry for the Layers panel's selection square 2026-10-10 20:07:31 +00:00
aiongg e33cb52248 Merge layers-drag: drag layers and objects to reorder them in the Layers panel (#371) 2026-10-10 20:07:20 +00:00
aiongg 1b9125ceea Layers: drag layers and objects to reorder them
- object.reorder {ids, above|below: id | index, layer?}: restacks sibling
  objects in front of or behind a target, or at an index counted from the
  top of a layer, moving them to that layer. Group members stay in their
  group. Bad input is an error and leaves the document unchanged.
- layer.move rejects a missing id or an out-of-range index.
- Layers panel: drag a layer row to reorder layers, an object row to
  restack it or move it to another layer, and a filled selection square
  onto a layer to move the selection there; a line or box shows the drop.
  Groups expand to list their members. Layers list top (frontmost) first,
  matching the stacking order.
2026-10-10 20:06:34 +00:00
aiongg 20d4178c43 Tables: cell edge gap colour and tint, all stroke types on cell edges, inner horizontal/vertical edge choice
CellStroke and cell/table style edge attributes carry gap colour and gap tint
(IDML ...EdgeStrokeGapColor/GapTint, ...BorderStrokeGapColor/GapTint). The table
renderer and PDF export draw every stroke type on cell edges, with the gap colour
under dashes, dots and stripes.

table.setCell validates stroke values, takes gapColor/gapTint and an edges list
(top/left/bottom/right are the target range's outer sides; innerHorizontal and
innerVertical the lines between its rows and columns). table.getCellStroke reports
the shown values of the chosen edges, null where they differ.
2026-10-10 20:04:57 +00:00
aiongg 74eda5579f Merge canvas-context-menu: the menu reopens on a second right-click, blocks both panes, and follows menu hiding 2026-10-10 19:29:37 +00:00
aiongg 1fe1ec9cc6 UI: canvas context menu reopens on a second right-click; menu keeps both panes' input
- A right-click while the menu is open closes it as a click outside;
  the request now stays until a frame ends with the menu open, so the
  menu reopens at the new click with the new target selected.
- While a context menu is open in either split-view pane, neither pane
  takes pointer presses, guide drags or keys. The open state is read
  once per frame, so the Escape or click that closes pane 0's menu does
  not reach pane 1.
- Submenus copied from the menu bar (Arrange, Select, Fitting, Type
  submenus...) are keyed by their menu bar path, so rows hidden with
  Edit > Menus are hidden in the context menu too, with Show All Menu
  Items below.

Tests: reopening on another object, Escape in split view, Escape with a
non-selection tool and a selection, the Type tool's keep-or-place-caret
rule, and hidden rows in a context submenu.
2026-10-10 19:29:13 +00:00
aiongg d5fb84d5e1 Merge nobreak-justify: jidori runs keep their width; tests for nonbreaking-space lines 2026-10-10 19:22:40 +00:00
aiongg 0474a8b5ec Compose: jidori runs keep their width when their spaces could stretch; tests for nonbreaking-space lines 2026-10-10 19:22:22 +00:00
aiongg d7d6fa8302 Integration: German entry for Rotate 180° 2026-10-10 19:13:45 +00:00
aiongg 1553acb6be Merge canvas-context-menu: a context menu on the canvas for objects, text and the page
Conflicts in ui-egui canvas.rs (fmt_tick stays pub(crate) for the ruler zero point; the open menu also
blocks the zero point drag; #84's press counting keeps its clicks with the branch's in_view; the tool
keyboard return keeps keyboard_pane; tests: both) and menus.rs (shortcuts return while an IME composes or
a canvas context menu is open).
2026-10-10 19:13:41 +00:00
aiongg 1194119c3e UI: a context menu on the canvas for objects, text and the page
Right-clicking the canvas opens a menu built from the menu bar's rows
(labels, shortcuts, check marks, greyed entries, translations):

- On an object: the object is selected first unless it already is, as
  the Selection tool would. Undo/Redo, Cut/Copy/Paste/Paste Into/Paste
  in Place, Transform (rotate 90° both ways, 180°, flip), Arrange,
  Select, Group/Ungroup, Lock/Unlock All, Hide/Show All, Fitting for
  placed graphics, Content, Effects, and Fill with Placeholder Text and
  Text Frame Options for text frames.
- While typing: a click in a text frame places the caret there, except
  inside the selected text, which stays selected. Cut/Copy/Paste/Paste
  without Formatting, the Insert Special Character, White Space and
  Break Character submenus, Fill with Placeholder Text, Change Case,
  Hidden Characters, Story Editor, Select All.
- On the page or pasteboard: Undo/Redo, Paste, Paste in Place, zoom,
  Rulers, Grids & Guides, Select All.

Tools only see the primary button, so a right-click or right-drag
starts no gesture. While the menu is open, Escape and the click that
closes it go to the menu, not to the tools or shortcuts. Each split-view
pane has its own menu.
2026-10-10 19:11:39 +00:00
aiongg 5b060a8de2 Merge nobreak-justify: No Break runs and nonbreaking spaces stretch on justified lines (#368)
Conflicts in compose breaker.rs (box_elastic keeps next's mojikumi stretch and shrink and adds them to
the word-space elasticity of No Break spaces; space_elastic uses is_word_space) and lib.rs (word spacing
uses is_word_space). next's leftover-stretch sharing and space_overflow also use is_word_space, so U+00A0
shares the stretch past the maximum; breaker::elastic_space is gone.
2026-10-10 18:56:46 +00:00
aiongg 42cfc8b06c Compose: No Break runs and nonbreaking spaces stretch on justified lines (#368) 2026-10-10 18:54:54 +00:00
aiongg 6d30b39a41 Merge #369: copied objects paste on the spread in view
Conflict in DesignApp::run: the spread is added after the system clipboard step from #84.
2026-10-10 18:48:47 +00:00
aiongg 5fae1ac2cc Merge upstream main a127c6d: progress docs (#355); ROADMAP.md takes upstream's rewrite 2026-10-10 18:47:02 +00:00
Brandon ThomasandClaude Opus 5.5 a127c6d5c3 Progress docs: target-app parity, gaps, alpha gate, readiness by audience (#355)
Progress docs per craftrules standards/progress-docs.md: target-app parity, gaps, roadmap with alpha gate, readiness by audience (full / mainstream / essentials) with Opus 5.5 hours, and feature, format, hardware, UI and localization parity docs.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-10 14:09:17 -04:00
noah1400andClaude Opus 5.5 dfdc650318 Paste: copied objects land on the spread in view (#348)
Paste and Paste in Place always put the objects on the first spread,
whatever page was showing. They now go to the spread in view, or to
the one a caller names with `spread`. With facing pages the objects
keep their distance from the spine, so they stay on their side of the
spread, also on a first or last page that sits alone.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-10 19:08:43 +02:00
aiongg c234a61ed4 Merge feat/cjk-typography-ui: the CJK style dialog tests install the UI fonts 2026-10-10 17:06:21 +00:00
aiongg e2ffa89817 UI: the CJK style dialog tests draw with the UI fonts installed
The section headings use the semibold family, which a bare egui context has no fonts
for; the tests install the UI fonts as the other dialog tests do.
2026-10-10 17:06:21 +00:00
aiongg b7efb71c05 Merge feat/ruler-zero-point: the page-origin ruler test sets the page origin 2026-10-10 16:58:28 +00:00
aiongg d59687bf96 Rulers: the page-origin ruler test sets the page origin before it reads the pieces
The loop above ends on the spine origin, which has a single ruler piece.
2026-10-10 16:58:24 +00:00
aiongg 0cd3a309da Integration: German entries for the ruby, kenten, shatai and grid strings and the drop cap strings
feat/cjk-typography-ui adds shared-table keys without German rows in de.rs, and eight
drop cap keys had none before. The rows copy the shared table's German column. The
Japanese table's 'Select an object to color its fill or stroke.' gets a German row of its
own, so de.rs covers every key its header lists.
2026-10-10 16:53:49 +00:00
aiongg b3cb8ed570 Integration: one Em Box Top and Em Box Bottom row in the shared and Japanese tables
feat/cjk-typography-ui (grid reference choices) and feat/paragraph-settings-full (border
and shading offsets) both add these keys; the tables hold each key once. The paragraph
settings rows stay.
2026-10-10 16:53:49 +00:00
aiongg b98d54ee38 Integration: IDML import warns when it repairs a tab list
#343's TabStop::sanitized_list repairs a file's tab list (dropped, clamped, shortened or
duplicate stops, more than MAX_TAB_STOPS); fix/idml-missing-spread's import_idml_report
carries the import warnings. The import counts the lists it had to repair and reports
them in one warning; sorting and a char stop's default '.' don't count.
2026-10-10 16:48:01 +00:00
aiongg 2589699057 Integration: the em box top/bottom leading test sets the Japanese composer
feat/cjk-typography's cjk_aki_below_measures_em_tops_and_aki_above_em_bottoms used the
default composer. #330's line (5dc8383a) applies leading models only under the Japanese
composers, so the test sets one.
2026-10-10 16:45:56 +00:00
aiongg fb727aa1b9 Integration: #330's Aki Below test measures the em box tops
#330 wrote cjk_aki_below_sets_the_upper_lines_leading_below_it on a base where Aki
Below measured from the em box bottom. feat/cjk-typography measures it from the em box
top (as the corpus shows), so the test asserts that the lower line's em box top sits the
upper line's leading below the upper line's.
2026-10-10 16:45:36 +00:00
aiongg a4ac6b039c Merge #343 update: Tabs commands return the stored list; tab lists from files are sanitized
Conflict: crates/idml/src/tests.rs: both tests (next's CJK settings and ruby round trips, the branch's hostile tab list import)
2026-10-10 16:44:40 +00:00
aiongg ba46313fc7 Integration: a Jump Object wrap steps by the Aki Below advance
#330 advances a line under the Japanese composers' Aki Below model by the upper line's
leading; the Jump Object wrap from the layout-parity chain stepped by the lower line's
leading. Both now use the same advance.
2026-10-10 16:44:13 +00:00
aiongg c0dc1503c8 Integration: format the kenten character test (rustfmt) 2026-10-10 16:44:06 +00:00
aiongg 9f1f41fb7b Integration: the kenten character test reads the mark from the run style's kenten mark
#84's kenten_character_change_keeps_kerning read RunStyle::kenten_character, which
feat/cjk-typography replaces with kenten_mark (kind, character, size, placement). The
test reads the mark text from it; the unchanged character draws the default sesame dot.
2026-10-10 16:43:32 +00:00
aiongg 0f6f96ae6d Merge feat/cjk-typography-ui: ruby, kenten, shatai, auto tate-chu-yoko, rotate roman, roman word break, grid references and the CJK style dialog panes
Conflict: ROADMAP.md: next's FONT1-3 lines with the branch's CJK1 line
Conflict: docs/cjk.md: the branch's rows, with next's aki below and Japanese composer text kept in the leading model row
Conflict: crates/fonts/src/fontdb.rs: both fields (family/style aliases and the ICF cache)
Conflict: crates/compose/src/ruby.rs: the branch's ruby module; its PlacedGlyph (and kenten.rs's) carry next's rendered_char
Conflict: crates/compose/src/lib.rs: modules both; rtl and para_block both; the branch's grid placement (gyoudori, grid references) replaces next's snap, its paragraph-gyoudori span uses next's line_metrics with mark leading and #330's aki below advance; a wrap push moves the line by whole grid lines and its grid end with it; next's trimmed spaces and drop cap, then the branch's ruby and kenten annotation
Conflict: crates/compose/src/shape.rs: next's pieces loop and StyleRuns with the branch's auto tate-chu-yoko split (after marks join their base) and fit, and Upright mode in every shape_segment call; next's label fallback passes the mode on
Conflict: crates/compose/src/tests.rs: both sets of tests appended at the end
Conflict: crates/idml/src/export.rs: next's metadata and text variable writers, then the branch's CJK settings writers
Conflict: crates/idml/src/tests.rs: both tests
Conflict: crates/ui-egui/src/dialogs.rs: the branch's Ruby dialog default section (next's duplicate characterStyleOptions default dropped); next's section arms with the branch's style_cjk::section_ui
2026-10-10 16:42:01 +00:00
aiongg bac5b091ae Merge #330 update: under the Japanese composers a line sits the upper line's leading below it
Conflict: crates/compose/src/lib.rs: next's line_metrics (tops, mark leading, last_line_mark) and baseline grid snap with the branch's (reference, model) and aki_below advance passed to next_baseline; Above keeps next's span space after plus the branch's aki_below
2026-10-10 16:36:22 +00:00
aiongg 370084909e Integration: collapse the kinsoku set choice's nested if in style_cjk.rs
clippy -D warnings (collapsible_if) rejects feat/style-sections-cjk's nested if around serde_json::to_value in the Kinsoku Set menu on next; the condition and the let join in one let chain.
2026-10-10 16:33:32 +00:00
aiongg 3d3bed63cf Integration: drop blank lines at the end of ja.rs's table
The German entry commits a237e639 and 9cacd53d added no Japanese rows but left an empty line each before the table's end; cargo fmt removes them.
2026-10-10 16:33:32 +00:00
aiongg 9cacd53d1b Integration: German entries for the CJK style section strings
feat/style-sections-cjk adds shared-table keys for the CJK sections of Paragraph and Character Style Options. de.rs holds a row for every key of the shared table; the rows copy the shared table's German column. ja.rs has rows for them from the branch.
2026-10-10 16:31:54 +00:00
aiongg a237e6395f Integration: German entries for the paragraph style sections, borders, shading and list strings
feat/style-sections and feat/paragraph-settings-full add shared-table keys for Paragraph Style Options' sections and the paragraph border, shading, span and list settings. de.rs holds a row for every key of the shared table; the rows copy the shared table's German column. ja.rs already has rows for them from the branches.
2026-10-10 16:31:48 +00:00
aiongg 85860d1403 Integration: German and Japanese entries for the preset name, PDF crop and zero point strings
#325's update (Preset Name), fix/idml-interchange's placed PDF crop choice (Bounding Box) and feat/ruler-zero-point (Origin, Spine, Lock/Unlock Zero Point) add shared-table keys. de.rs and ja.rs hold a row for every key of the shared table; the rows copy the shared table's German and Japanese columns.
2026-10-10 16:31:39 +00:00
aiongg 23b6ce4cc1 Merge feat/ime: IME composition (#322)
Conflict: crates/ui-egui/src/lib.rs: next's missing-fonts test; the branch's side repeated control_bar_shows_its_second_row (next's newer copy stays) and key_names_sent_as_text_are_dropped, whose IME version replaces next's copy in place
2026-10-10 16:30:09 +00:00
aiongg 15167058b9 Merge fix/idml-missing-spread: a spread missing from the package is reported, and part names match leniently
Conflict: crates/engine/src/cmd/file.rs: next's file.open params (InDesign .indd/.indt) with the branch's package-parts warnings
Conflict: crates/engine/src/cmd/interchange.rs: next's file.openIdml params (InDesign files) with the branch's warnings list; import_report reads the branch's Imported report, then next's resolve_pdf_crops; open_idml keeps next's .indd conversion and title, then takes import_report's warnings after the conversion's; next's comment on not saving over the .idml or .indd
2026-10-10 16:29:16 +00:00
aiongg d7592ba6e0 Merge fix/paragraph-mark-leading: the paragraph mark's size counts in its line's auto leading
Conflict: crates/compose/src/lib.rs: next's mark_chars and mark_leading (empty paragraphs, 60712ded) kept; the branch's paragraph mark leading renamed last_line_mark (its second spacing_for dropped, next computes it above); line_metrics with next's arguments, then the last line's leading raised to last_line_mark as the branch does
Conflict: crates/compose/src/tests.rs: both sides' tests
2026-10-10 16:28:38 +00:00
aiongg c93664943b Merge feat/ruler-zero-point: a document zero point and ruler origin you can drag, reset and lock
Conflict: crates/idml/src/tests.rs: both sides' tests
2026-10-10 16:28:07 +00:00
aiongg 65a6a0ba7e Merge feat/style-sections-cjk: CJK sections in Paragraph and Character Style Options
Conflict: crates/engine/src/cmd/style.rs: both params notes in the paragraph style edit spec (startAt null, kinsoku null); create_para with next's set_json_over, continue_numbering and the branch's explicit_default_kinsoku; edit_para calls both helpers; both tests
Conflict: crates/ui-egui/src/dialogs.rs: next's section arms (advanced to bullets) and the branch's CJK section arm; next's paragraph helpers and paragraph_local before the branch's section_list (cjk flag, scrolling list; doc comment stays removed as on next)
The branch's "Lines:" row in the shared i18n table is dropped: next already has the key (drop caps).
2026-10-10 16:27:26 +00:00
aiongg 989373114b Tabs: tab lists from files are sanitized like the commands check them 2026-10-10 16:26:56 +00:00
aiongg 398182347a Integration: drop Ukrainian rows feat/style-sections repeats
feat/style-sections adds Ukrainian rows for Advanced Character Formats, OpenType Features and Tint:, which next already has from earlier PRs; the Ukrainian catalog test rejects duplicate keys. next's rows stay.
2026-10-10 16:26:15 +00:00
aiongg c019502806 Integration: close typo_ascent in fontdb.rs after the IDML interchange merge
The fix/idml-interchange merge (c3c24a0b) kept next's typo_ascent (#81/#129 metrics) and the branch's plain_family side by side but lost the closing brace between them, so designcraft-fonts did not compile.
2026-10-10 16:26:15 +00:00
aiongg 0ebe1212f0 Merge feat/paragraph-settings-full: paragraph borders, shading, span space and list levels in the model, layout, IDML and dialogs
Conflict: crates/compose/src/lib.rs: imports from both (ListAlign, ListCounter; ParaBox beside next's hit_note_with); the branch's list labels (ListCounter, named_labels, label_chars, label alignment, Tab Position stop) with next's list_label marking from prepend_label's count; the branch's align_label before next's warichu placement, trimmed spaces and drop cap; next's rule_color for rules above and below in the branch's Deco literals; the branch's split block end (ends_split, span space after) in place of next's two identical copies; next's drop cap helpers, then the branch's label_chars and align_label, then prepend_label
Conflict: crates/compose/src/tests.rs: both sides' tests
Conflict: crates/idml/src/export.rs: next's para_attrs parent name argument with the branch's with_list_tab (its parent attributes renamed parent_props) for styles and paragraph ranges
Conflict: crates/idml/src/import.rs: next's INDESIGN_CORNER_SIZE and tint doc; the branch's corners() placed before tint's doc comment
Conflict: crates/idml/src/tests.rs: both sides' tests
Conflict: crates/ui-egui/src/dialogs.rs: next's deleteParagraphStyle and the branch's paragraphLocal confirm arms
Conflict: crates/ui-egui/src/panels/glyphs.rs: the branch's grid() split, with next's scroll bar room in its column count
2026-10-10 16:26:10 +00:00
aiongg 4014dac6c2 Compose: under the Japanese composers a line sits the upper line's leading below it
Under the Aki Below leading model a line's leading is the space below it, so the
next line's reference point sits the upper line's leading below the upper line's
(InDesign's Japanese-composer output measures this in four corpus documents).
The first line in a frame or column places itself with its own leading; space
before and after adds on top, and the baseline grid snaps the result. The other
leading models advance by the lower line's leading as before.
2026-10-10 16:22:17 +00:00