Skip to content

fix: align rtl date token rendering with word parity#3250

Merged
caio-pizzol merged 4 commits into
mainfrom
artem/SD-3098
May 12, 2026
Merged

fix: align rtl date token rendering with word parity#3250
caio-pizzol merged 4 commits into
mainfrom
artem/SD-3098

Conversation

@artem-harbour
Copy link
Copy Markdown
Contributor

@artem-harbour artem-harbour commented May 12, 2026

Linear: SD-3098

Proposal:
Fix RTL date rendering parity with Word by propagating run-level bidi metadata (w:rtl) into DomPainter and applying targeted run-direction handling at paint time. In this approach, RTL date-like runs receive dir="rtl" plus render-time RLM separator normalization, while date-like LTR runs inside RTL paragraphs receive dir="ltr" to prevent separator drift. The proposal also includes preserving bidi boundaries in run-merge signatures and adding unit + behavior coverage with a real rtl-dates.docx fixture.

@artem-harbour artem-harbour self-assigned this May 12, 2026
@linear
Copy link
Copy Markdown

linear Bot commented May 12, 2026

SD-3098

@codecov-commenter
Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.

📢 Thoughts on this report? Let us know!

@artem-harbour artem-harbour requested a review from caio-pizzol May 12, 2026 17:02
@artem-harbour artem-harbour marked this pull request as ready for review May 12, 2026 17:06
@artem-harbour artem-harbour requested a review from a team as a code owner May 12, 2026 17:06
Copy link
Copy Markdown

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 4934522294

ℹ️ About Codex in GitHub

Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".

Comment thread packages/layout-engine/pm-adapter/src/attributes/paragraph.ts Outdated
Fix RTL date rendering parity with Word per SD-3098. The browser's UBA does
not reorder numerics inside an RTL run the way Word does, and run-boundary
separator drift breaks mixed-direction date strings like `-03-23` + `2026`.

The fix is paint-time only - it never touches PM/model/export:

1. DomPainter sets dir="rtl" on the span when run.bidi.rtl === true (per-run
   bidi isolation eliminates run-boundary separator drift)
2. DomPainter sets dir="ltr" on date-like LTR runs (per regex) inside RTL
   contexts (prevents the third case where a non-rtl date inside an rtl
   paragraph reorders unpredictably)
3. normalizeRtlDateTokenForWordParity injects U+200F (RLM) around `./- `
   separators inside RTL date-like text so Word and SuperDoc render the
   same visual order (e.g. XML `23/03/2026` -> visual `2026/03/23`)

Three test cases in rtl-dates.docx (the Linear-attached "Date Being Weird"
fixture):
- Header: single <w:rtl/> run `23/03/2026` -> Word visual `2026/03/23`
- Body 1: LTR run `-03-23` + RTL run `2026` -> Word visual `2026-03-23`
- Body 2 (control): single LTR run `2026/03/26` -> unchanged

Other changes:
- bidiCompatible guard in mergeAdjacentRuns: prevents a <w:rtl/> run from
  merging with a plain run and silently losing the bidi flag
- run-visual-marks.ts and versionSignature.ts: include run.bidi in the
  caching hashes so a rtl-only edit invalidates measure/DOM cache
- New painter unit tests (rtl-date-parity.test.ts) verifying dir + RLM
- New behavior spec (rtl-dates-word-parity.spec.ts) using the real fixture

This PR builds on the run-level bidi metadata SD-2781 (#3203) added to the
TextRun contract - reads from TextRun.bidi.rtl (the merged shape), not a
parallel RunMarks.bidiContext field.
caio-pizzol and others added 3 commits May 12, 2026 15:57
… cases

Adds pre-merge coverage for SD-3098 rendering invariants:

- hashRunVisualMarks: bidi field changes the dirty-run hash (rtl=true vs
  absent, rtl=true vs rtl=false, embedding-only changes). Stale hashes
  would let an edit that flips just <w:rtl/> reuse stale measure/DOM.
- deriveBlockVersion: bidi flips invalidate the cached block version.
  Without this, the painter would reuse a cached block snapshot after
  an rtl-only edit.
- DomPainter painter tests: mixed rtl + ltr runs on the same line stay
  as separate spans with distinct dir attrs; non-date-like rtl runs
  keep dir="rtl" without RLM injection; non-rtl plain text leaves the
  span without a dir attribute.

Also adds rtl-mixed-run-line.docx + behavior spec as a negative test
asserting Hebrew + date + Hebrew paragraphs don't regress (Hebrew runs
stay rtl, date run is not RLM-injected since it isn't rtl-tagged).
Copy link
Copy Markdown
Contributor

@caio-pizzol caio-pizzol left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

hey @artem-harbour - i pulled main in, switched this to the rtl field #3203 added (got renamed after you opened this), wired rtl into the cache keys so an edit that flips rtl doesn't reuse old DOM, and stopped pm-adapter from merging runs with different rtl.

follow-up commit adds tests plus a Hebrew + date Word fixture. both fixtures in the corpus, all three dates in Date Being Weird.docx render right now.

lgtm.

@caio-pizzol caio-pizzol enabled auto-merge (squash) May 12, 2026 19:23
@caio-pizzol caio-pizzol merged commit f31c05b into main May 12, 2026
64 checks passed
@caio-pizzol caio-pizzol deleted the artem/SD-3098 branch May 12, 2026 19:41
@superdoc-bot
Copy link
Copy Markdown
Contributor

superdoc-bot Bot commented May 12, 2026

🎉 This PR is included in vscode-ext v2.3.0-next.123

@superdoc-bot
Copy link
Copy Markdown
Contributor

superdoc-bot Bot commented May 12, 2026

🎉 This PR is included in @superdoc-dev/mcp v0.3.0-next.78

The release is available on GitHub release

@superdoc-bot
Copy link
Copy Markdown
Contributor

superdoc-bot Bot commented May 12, 2026

🎉 This PR is included in @superdoc-dev/react v1.2.0-next.121

The release is available on GitHub release

@superdoc-bot
Copy link
Copy Markdown
Contributor

superdoc-bot Bot commented May 12, 2026

🎉 This PR is included in superdoc-cli v0.8.0-next.95

The release is available on GitHub release

@superdoc-bot
Copy link
Copy Markdown
Contributor

superdoc-bot Bot commented May 12, 2026

🎉 This PR is included in superdoc v1.30.0-next.77

The release is available on GitHub release

@superdoc-bot
Copy link
Copy Markdown
Contributor

superdoc-bot Bot commented May 12, 2026

🎉 This PR is included in superdoc-sdk v1.8.0-next.77

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants