Skip to content

layout: Fix line breaking opportunities for Chinese and Japanese - #43744

Merged
Loirooriol merged 5 commits into
servo:mainfrom
SharanRP:fix-43677-text-wrap-overflow
Apr 5, 2026
Merged

layout: Fix line breaking opportunities for Chinese and Japanese#43744
Loirooriol merged 5 commits into
servo:mainfrom
SharanRP:fix-43677-text-wrap-overflow

Conversation

@SharanRP

@SharanRP SharanRP commented Mar 29, 2026

Copy link
Copy Markdown
Contributor

Enable CJK-aware line breaking in inline layout so Chinese/Japanese text gets proper wrap opportunities instead of overflowing containers.

Testing: some WPT are now passing

@servo-highfive servo-highfive added the S-awaiting-review There is new code that needs to be reviewed. label Mar 29, 2026
@TimvdLippe TimvdLippe added the T-linux-wpt Do a try run of the WPT label Mar 29, 2026
@github-actions github-actions Bot removed the T-linux-wpt Do a try run of the WPT label Mar 29, 2026
@github-actions

Copy link
Copy Markdown

🔨 Triggering try run (#23704025326) for Linux (WPT)

@Loirooriol Loirooriol left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

The testcase from #43677 doesn't seem to use japanese/chinese at all?

Comment thread components/layout/flow/inline/mod.rs Outdated
@github-actions

Copy link
Copy Markdown

Test results for linux-wpt from try job (#23704025326):

Flaky unexpected result (17)
  • CRASH [expected OK] /_webgl/conformance/glsl/implicit/subtract_ivec3_vec3.vert.html
  • CRASH [expected OK] /html/canvas/element/color-type/2d.color.type.u8srgb.to.f16p3.to.u8srgb.html
  • OK /html/semantics/document-metadata/the-meta-element/pragma-directives/attr-meta-http-equiv-refresh/allow-scripts-flag-changing-1.html (#39694)
    • PASS [expected FAIL] subtest: Meta refresh is blocked by the allow-scripts sandbox flag at its creation time, not when refresh comes due
  • OK /html/semantics/embedded-content/media-elements/audio_loop_seek_to_eos.html (#41226)
    • PASS [expected FAIL] subtest: seeking to the end of looping audio
  • TIMEOUT [expected OK] /html/semantics/embedded-content/the-iframe-element/iframe_sandbox_navigate_other_frame_popup.sub.html (#39702)
    • TIMEOUT [expected FAIL] subtest: Sandboxed iframe can not navigate other frame's popup

      Test timed out
      

  • OK /html/semantics/forms/form-submission-0/jsurl-form-submit.tentative.html (#36489)
    • PASS [expected FAIL] subtest: Verifies that form submissions scheduled inside javascript: urls take precedence over the javascript: url's return value.
  • OK /html/semantics/scripting-1/the-script-element/module/dynamic-import/blob-url.any.worker-module.html (#43510)
    • FAIL [expected PASS] subtest: Revoking a blob URL immediately after calling import will not fail

      promise_test: Unhandled rejection with value: object "TypeError: Module fetching failed"
      

  • OK /html/webappapis/user-prompts/print-during-unload.html (#35944)
    • FAIL [expected PASS] subtest: print() during unload

      assert_array_equals: expected property 1 to be "destination" but got "error: window.print is not a function" (expected array ["start", "destination"] got ["start", "error: window.print is not a function"])
      

  • OK /mixed-content/tentative/autoupgrades/audio-upgrade.https.sub.html (#41697)
    • FAIL [expected PASS] subtest: Audio of other host autoupgraded

      assert_equals: Length of other host audio is correct expected 1 but got Infinity
      

  • PASS [expected FAIL] /png/apng/acTL-plays-one.html (#41218)
  • TIMEOUT [expected OK] /referrer-policy/css-integration/svg/internal-stylesheet.html
    • TIMEOUT [expected FAIL] subtest: Styling SVG from internal styles mask-image

      Test timed out
      

  • OK /resource-timing/buffer-full-add-then-clear.html (#40819)
    • FAIL [expected PASS] subtest: Test that if the buffer is cleared after entries were added to the secondary buffer, those entries make it into the primary one

      assert_equals: Number of entries does not match the expected value. expected 3 but got 0
      

  • OK /resource-timing/test_resource_timing.html (#25720)
    • PASS [expected FAIL] subtest: PerformanceEntry has correct name, initiatorType, startTime, and duration (link)
  • TIMEOUT /trusted-types/trusted-types-navigation.html?06-10 (#37920)
    • TIMEOUT [expected FAIL] subtest: Navigate a frame via anchor with javascript:-urls in report-only mode.

      Test timed out
      

    • NOTRUN [expected TIMEOUT] subtest: Navigate a frame via anchor with javascript:-urls w/ default policy in report-only mode.
  • OK /webdriver/tests/classic/element_click/center_point.py
    • FAIL [expected PASS] subtest: test_entirely_in_view

      webdriver.error.NoSuchWindowException: no such window (404): No such window
      

  • OK /webdriver/tests/classic/element_click/file_upload.py
    • FAIL [expected PASS] subtest: test_file_upload_state

      webdriver.error.NoSuchWindowException: no such window (404): No such window
      

  • OK /webdriver/tests/classic/perform_actions/wheel_events.py
    • FAIL [expected PASS] subtest: test_scroll_on_not_scrollable_element[delta-x]

      webdriver.error.NoSuchWindowException: no such window (404): No such window
      

Stable unexpected results that are known to be intermittent (19)
  • TIMEOUT /FileAPI/url/url-in-tags-revoke.window.html (#19978)
    • PASS [expected TIMEOUT] subtest: Fetching a blob URL immediately before revoking it works in <script> tags.
  • FAIL [expected PASS] /_mozilla/mozilla/sslfail.html (#10760)
  • TIMEOUT [expected OK] /_mozilla/mozilla/window_resize_event.html (#36741)
    • TIMEOUT [expected PASS] subtest: Popup onresize event fires after resizeTo

      Test timed out
      

  • CRASH [expected PASS] /_mozilla/shadow-dom/move-element-with-ua-shadow-tree-crash.html (#39473)
  • CRASH [expected OK] /content-security-policy/meta/sandbox-iframe.html (#43478)
  • OK /css/css-fonts/generic-family-keywords-001.html (#37467)
    • PASS [expected FAIL] subtest: @font-face matching for quoted and unquoted generic(fangsong)
  • OK /css/css-fonts/generic-family-keywords-003.html (#38994)
    • PASS [expected FAIL] subtest: @font-face matching for quoted and unquoted sans-serif (drawing text in a canvas)
    • PASS [expected FAIL] subtest: @font-face matching for quoted and unquoted math (drawing text in a canvas)
    • PASS [expected FAIL] subtest: @font-face matching for quoted and unquoted generic(fangsong) (drawing text in a canvas)
    • PASS [expected FAIL] subtest: @font-face matching for quoted and unquoted generic(khmer-mul) (drawing text in a canvas)
    • PASS [expected FAIL] subtest: @font-face matching for quoted and unquoted ui-serif (drawing text in a canvas)
    • PASS [expected FAIL] subtest: @font-face matching for quoted and unquoted ui-sans-serif (drawing text in a canvas)
  • OK /dom/nodes/moveBefore/iframe-document-preserve.window.html (#43152)
    • FAIL [expected PASS] subtest: moveBefore(): cross-origin iframe is preserved: remove self via innerHTML

      assert_equals: iframe does not fire a second load event expected 1 but got 0
      

  • ERROR [expected OK] /fetch/fetch-later/quota/same-origin-iframe/accumulated-oversized-payload.https.window.html (#41705)
  • OK [expected ERROR] /fetch/fetch-later/quota/same-origin-iframe/sandboxed-iframe.https.window.html (#41704)
  • OK /fetch/metadata/generated/css-font-face.https.sub.tentative.html (#32732)
    • PASS [expected FAIL] subtest: sec-fetch-mode
    • PASS [expected FAIL] subtest: sec-fetch-dest
  • ERROR /fetch/metadata/generated/serviceworker.https.sub.html (#36247)
    • PASS [expected FAIL] subtest: sec-fetch-site - Same origin, no options - registration
  • ERROR [expected OK] /focus/focus-event-after-switching-iframes.sub.html (#40368)
  • OK /html/browsers/browsing-the-web/navigating-across-documents/navigation-unload-same-origin-fragment.html (#20768)
    • PASS [expected FAIL] subtest: Tests that a fragment navigation in the unload handler will not block the initial navigation
  • OK /html/browsers/browsing-the-web/navigating-across-documents/navigation-unload-same-origin.window.html (#29049)
    • PASS [expected FAIL] subtest: Same-origin navigation started from unload handler must be ignored
  • OK /html/browsers/browsing-the-web/navigating-across-documents/refresh/same-document-refresh.html (#34597)
    • FAIL [expected PASS] subtest: Same-Document Referrer from Refresh

      assert_equals: original page loads expected "http://web-platform.test:8000/html/browsers/browsing-the-web/navigating-across-documents/refresh/resources/refresh-with-section.sub.html?url=%23section" but got "http://web-platform.test:8000/html/browsers/browsing-the-web/navigating-across-documents/refresh/resources/refresh-with-section.sub.html?url=%23section#section"
      

  • OK /navigation-timing/test-navigation-type-reload.html (#33334)
    • PASS [expected FAIL] subtest: Reload domComplete > Original domComplete
    • PASS [expected FAIL] subtest: Reload domContentLoadedEventEnd > Original domContentLoadedEventEnd
    • PASS [expected FAIL] subtest: Reload domContentLoadedEventStart > Original domContentLoadedEventStart
    • PASS [expected FAIL] subtest: Reload domInteractive > Original domInteractive
    • PASS [expected FAIL] subtest: Reload fetchStart > Original fetchStart
    • PASS [expected FAIL] subtest: Reload loadEventEnd > Original loadEventEnd
    • PASS [expected FAIL] subtest: Reload loadEventStart > Original loadEventStart
  • OK /touch-events/single-tap-when-touchend-listener-use-sync-xhr.html (#41175)
    • FAIL [expected PASS] subtest: Click event should be fired when touchend opens synchronous XHR

      assert_equals: expected "touchend@div, mousedown@div, mouseup@div, click@div" but got "touchend@div"
      

  • OK [expected TIMEOUT] /trusted-types/trusted-types-navigation.html?26-30 (#38807)
    • PASS [expected TIMEOUT] subtest: Navigate a window via form-submission with javascript:-urls in report-only mode.
    • PASS [expected NOTRUN] subtest: Navigate a window via form-submission with javascript:-urls w/ default policy in report-only mode.
    • PASS [expected NOTRUN] subtest: Navigate a frame via form-submission with javascript:-urls in enforcing mode.
    • PASS [expected NOTRUN] subtest: Navigate a frame via form-submission with javascript:-urls w/ default policy in enforcing mode.
Stable unexpected results (23)
  • FAIL [expected PASS] /css/css-text/i18n/css3-text-line-break-opclns-207.html
  • FAIL [expected PASS] /css/css-text/i18n/css3-text-line-break-opclns-214.html
  • OK /css/css-text/i18n/ja/css-text-line-break-ja-cpm-loose.html
    • PASS [expected FAIL] subtest: 30FB KATAKANA MIDDLE DOT may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FF1A FULLWIDTH COLON may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FF1B FULLWIDTH SEMICOLON may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FF65 HALFWIDTH KATAKANA MIDDLE DOT may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 203C DOUBLE EXCLAMATION MARK may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2047 DOUBLE QUESTION MARK may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2048 QUESTION EXCLAMATION MARK may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2049 EXCLAMATION QUESTION MARK may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FF01 FULLWIDTH EXCLAMATION MARK may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FF1F FULLWIDTH QUESTION MARK may appear at line start if ja and loose
  • OK /css/css-text/i18n/ja/css-text-line-break-ja-hyphens-loose.html
    • PASS [expected FAIL] subtest: 301C WAVE DASH may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 30A0 KATAKANA-HIRAGANA DOUBLE HYPHEN may appear at line start if ja and loose
  • OK /css/css-text/i18n/ja/css-text-line-break-ja-hyphens-normal.html
    • PASS [expected FAIL] subtest: 301C WAVE DASH may appear at line start if ja and normal
    • PASS [expected FAIL] subtest: 30A0 KATAKANA-HIRAGANA DOUBLE HYPHEN may appear at line start if ja and normal
  • OK /css/css-text/i18n/ja/css-text-line-break-ja-po-loose.html
    • PASS [expected FAIL] subtest: 00B0 DEGREE SIGN may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2030 PER MILLE SIGN may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2032 PRIME may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2033 DOUBLE PRIME may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2035 REVERSED PRIME may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2103 DEGREE CELSIUS may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2109 DEGREE FAHRENHEIT may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FE6A SMALL PERCENT SIGN may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FF05 FULLWIDTH PERCENT SIGN may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FFE0 FULLWIDTH CENT SIGN may appear at line start if ja and loose
  • OK /css/css-text/i18n/other-lang/css-text-line-break-de-cpm-loose.html
    • FAIL [expected PASS] subtest: 30FB KATAKANA MIDDLE DOT may NOT appear at line start if de and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: FF1A FULLWIDTH COLON may NOT appear at line start if de and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: FF1B FULLWIDTH SEMICOLON may NOT appear at line start if de and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: FF65 HALFWIDTH KATAKANA MIDDLE DOT may NOT appear at line start if de and loose

      assert_approx_equals: expected 84 +/- 1 but got 54
      

    • FAIL [expected PASS] subtest: 203C DOUBLE EXCLAMATION MARK may NOT appear at line start if de and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: 2047 DOUBLE QUESTION MARK may NOT appear at line start if de and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: 2048 QUESTION EXCLAMATION MARK may NOT appear at line start if de and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: 2049 EXCLAMATION QUESTION MARK may NOT appear at line start if de and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: FF01 FULLWIDTH EXCLAMATION MARK may NOT appear at line start if de and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: FF1F FULLWIDTH QUESTION MARK may NOT appear at line start if de and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

  • OK /css/css-text/i18n/other-lang/css-text-line-break-de-hyphens-loose.html
    • FAIL [expected PASS] subtest: 301C WAVE DASH may NOT appear at line start if de and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: 30A0 KATAKANA-HIRAGANA DOUBLE HYPHEN may NOT appear at line start if de and loose

      assert_approx_equals: expected 84 +/- 1 but got 54
      

  • OK /css/css-text/i18n/other-lang/css-text-line-break-de-hyphens-normal.html
    • FAIL [expected PASS] subtest: 301C WAVE DASH may NOT appear at line start if de and normal

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: 30A0 KATAKANA-HIRAGANA DOUBLE HYPHEN may NOT appear at line start if de and normal

      assert_approx_equals: expected 84 +/- 1 but got 54
      

  • OK /css/css-text/i18n/other-lang/css-text-line-break-de-po-loose.html
    • FAIL [expected PASS] subtest: 00B0 DEGREE SIGN may NOT appear at line start if de and loose

      assert_approx_equals: expected 81 +/- 1 but got 51
      

    • FAIL [expected PASS] subtest: 2030 PER MILLE SIGN may NOT appear at line start if de and loose

      assert_approx_equals: expected 100 +/- 1 but got 70
      

    • FAIL [expected PASS] subtest: 2032 PRIME may NOT appear at line start if de and loose

      assert_approx_equals: expected 77 +/- 1 but got 47
      

    • FAIL [expected PASS] subtest: 2033 DOUBLE PRIME may NOT appear at line start if de and loose

      assert_approx_equals: expected 82 +/- 1 but got 52
      

    • FAIL [expected PASS] subtest: 2035 REVERSED PRIME may NOT appear at line start if de and loose

      assert_approx_equals: expected 77 +/- 1 but got 47
      

    • FAIL [expected PASS] subtest: 2103 DEGREE CELSIUS may NOT appear at line start if de and loose

      assert_approx_equals: expected 100 +/- 1 but got 70
      

    • FAIL [expected PASS] subtest: 2109 DEGREE FAHRENHEIT may NOT appear at line start if de and loose

      assert_approx_equals: expected 96 +/- 1 but got 66
      

    • FAIL [expected PASS] subtest: FE6A SMALL PERCENT SIGN may NOT appear at line start if de and loose

      assert_approx_equals: expected 80 +/- 1 but got 50
      

    • FAIL [expected PASS] subtest: FF05 FULLWIDTH PERCENT SIGN may NOT appear at line start if de and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: FFE0 FULLWIDTH CENT SIGN may NOT appear at line start if de and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

  • OK /css/css-text/i18n/unknown-lang/css-text-line-break-cpm-loose.html
    • FAIL [expected PASS] subtest: 30FB KATAKANA MIDDLE DOT may NOT appear at line start if lang unknown and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: FF1A FULLWIDTH COLON may NOT appear at line start if lang unknown and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: FF1B FULLWIDTH SEMICOLON may NOT appear at line start if lang unknown and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: FF65 HALFWIDTH KATAKANA MIDDLE DOT may NOT appear at line start if lang unknown and loose

      assert_approx_equals: expected 84 +/- 1 but got 54
      

    • FAIL [expected PASS] subtest: 203C DOUBLE EXCLAMATION MARK may NOT appear at line start if lang unknown and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: 2047 DOUBLE QUESTION MARK may NOT appear at line start if lang unknown and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: 2048 QUESTION EXCLAMATION MARK may NOT appear at line start if lang unknown and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: 2049 EXCLAMATION QUESTION MARK may NOT appear at line start if lang unknown and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: FF01 FULLWIDTH EXCLAMATION MARK may NOT appear at line start if lang unknown and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: FF1F FULLWIDTH QUESTION MARK may NOT appear at line start if lang unknown and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

  • OK /css/css-text/i18n/unknown-lang/css-text-line-break-hyphens-loose.html
    • FAIL [expected PASS] subtest: 301C WAVE DASH may NOT appear at line start if lang unknown and loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: 30A0 KATAKANA-HIRAGANA DOUBLE HYPHEN may NOT appear at line start if lang unknown and loose

      assert_approx_equals: expected 84 +/- 1 but got 54
      

  • OK /css/css-text/i18n/unknown-lang/css-text-line-break-hyphens-normal.html
    • FAIL [expected PASS] subtest: 301C WAVE DASH may NOT appear at line start if lang unknown and normal

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: 30A0 KATAKANA-HIRAGANA DOUBLE HYPHEN may NOT appear at line start if lang unknown and normal

      assert_approx_equals: expected 84 +/- 1 but got 54
      

  • OK /css/css-text/i18n/unknown-lang/css-text-line-break-po-loose.html
    • FAIL [expected PASS] subtest: 00B0 DEGREE SIGN may NOT appear at line start if loose

      assert_approx_equals: expected 81 +/- 1 but got 51
      

    • FAIL [expected PASS] subtest: 2030 PER MILLE SIGN may NOT appear at line start if loose

      assert_approx_equals: expected 100 +/- 1 but got 70
      

    • FAIL [expected PASS] subtest: 2032 PRIME may NOT appear at line start if loose

      assert_approx_equals: expected 77 +/- 1 but got 47
      

    • FAIL [expected PASS] subtest: 2033 DOUBLE PRIME may NOT appear at line start if loose

      assert_approx_equals: expected 82 +/- 1 but got 52
      

    • FAIL [expected PASS] subtest: 2035 REVERSED PRIME may NOT appear at line start if loose

      assert_approx_equals: expected 77 +/- 1 but got 47
      

    • FAIL [expected PASS] subtest: 2103 DEGREE CELSIUS may NOT appear at line start if loose

      assert_approx_equals: expected 100 +/- 1 but got 70
      

    • FAIL [expected PASS] subtest: 2109 DEGREE FAHRENHEIT may NOT appear at line start if loose

      assert_approx_equals: expected 96 +/- 1 but got 66
      

    • FAIL [expected PASS] subtest: FE6A SMALL PERCENT SIGN may NOT appear at line start if loose

      assert_approx_equals: expected 80 +/- 1 but got 50
      

    • FAIL [expected PASS] subtest: FF05 FULLWIDTH PERCENT SIGN may NOT appear at line start if loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

    • FAIL [expected PASS] subtest: FFE0 FULLWIDTH CENT SIGN may NOT appear at line start if loose

      assert_approx_equals: expected 99 +/- 1 but got 69
      

  • OK /css/css-text/i18n/zh/css-text-line-break-zh-cpm-loose.html
    • PASS [expected FAIL] subtest: 30FB KATAKANA MIDDLE DOT may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FF1A FULLWIDTH COLON may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FF1B FULLWIDTH SEMICOLON may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FF65 HALFWIDTH KATAKANA MIDDLE DOT may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 203C DOUBLE EXCLAMATION MARK may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2047 DOUBLE QUESTION MARK may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2048 QUESTION EXCLAMATION MARK may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2049 EXCLAMATION QUESTION MARK may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FF01 FULLWIDTH EXCLAMATION MARK may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FF1F FULLWIDTH QUESTION MARK may appear at line start if zh and loose
  • OK /css/css-text/i18n/zh/css-text-line-break-zh-hyphens-loose.html
    • PASS [expected FAIL] subtest: 301C WAVE DASH may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 30A0 KATAKANA-HIRAGANA DOUBLE HYPHEN may appear at line start if zh and loose
  • OK /css/css-text/i18n/zh/css-text-line-break-zh-hyphens-normal.html
    • PASS [expected FAIL] subtest: 301C WAVE DASH may appear at line start if zh and normal
    • PASS [expected FAIL] subtest: 30A0 KATAKANA-HIRAGANA DOUBLE HYPHEN may appear at line start if zh and normal
  • OK /css/css-text/i18n/zh/css-text-line-break-zh-po-loose.html
    • PASS [expected FAIL] subtest: 00B0 DEGREE SIGN may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2030 PER MILLE SIGN may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2032 PRIME may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2033 DOUBLE PRIME may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2035 REVERSED PRIME may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2103 DEGREE CELSIUS may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2109 DEGREE FAHRENHEIT may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FE6A SMALL PERCENT SIGN may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FF05 FULLWIDTH PERCENT SIGN may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FFE0 FULLWIDTH CENT SIGN may appear at line start if zh and loose
  • PASS [expected FAIL] /css/css-text/line-break/line-break-loose-013.xht
  • PASS [expected FAIL] /css/css-text/line-break/line-break-normal-013.xht
  • FAIL [expected PASS] /css/css-text/line-break/line-break-strict-013.xht
  • PASS [expected FAIL] /css/css-text/writing-system/writing-system-line-break-001.html
  • PASS [expected FAIL] /css/css-text/writing-system/writing-system-line-break-002.html

@github-actions

Copy link
Copy Markdown

⚠️ Try run (#23704025326) failed!

@SharanRP

Copy link
Copy Markdown
Contributor Author

I've totally refactored this to ditch the character sniffing, now it just checks for lang="ja" or lang="zh" using the computed _x_lang attribute.

@SharanRP
SharanRP force-pushed the fix-43677-text-wrap-overflow branch from 6fa759c to 80334ab Compare March 29, 2026 17:36
@Loirooriol Loirooriol added the T-linux-wpt Do a try run of the WPT label Mar 29, 2026
@github-actions github-actions Bot removed the T-linux-wpt Do a try run of the WPT label Mar 29, 2026
@github-actions

Copy link
Copy Markdown

🔨 Triggering try run (#23715380684) for Linux (WPT)

@github-actions

Copy link
Copy Markdown

Test results for linux-wpt from try job (#23715380684):

Flaky unexpected result (29)
  • CRASH [expected OK] /_webgl/conformance/glsl/implicit/subtract_int_vec2.vert.html
  • CRASH [expected OK] /_webgl/conformance/uniforms/no-over-optimization-on-uniform-array-07.html
  • OK /beacon/beacon-basic.https.window.html (#41723)
    • FAIL [expected PASS] subtest: Payload size restriction should be accumulated: type = string

      assert_false: expected false got true
      

  • CRASH [expected OK] /content-security-policy/meta/sandbox-iframe.html (#43478)
  • OK /css/css-cascade/layer-cssom-order-reverse.html (#36094)
    • FAIL [expected PASS] subtest: Delete layer invalidates @font-face

      assert_equals: expected "220px" but got "133px"
      

  • FAIL [expected PASS] /css/css-ui/appearance-menulist-button-001.html
  • OK [expected ERROR] /fetch/fetch-later/quota/cross-origin-iframe/sandboxed-iframe.https.window.html
  • ERROR [expected OK] /fetch/fetch-later/quota/same-origin-iframe/accumulated-oversized-payload.https.window.html (#41705)
  • ERROR /fetch/metadata/generated/serviceworker.https.sub.html (#36247)
    • PASS [expected FAIL] subtest: sec-fetch-site - Same origin, no options - registration
  • ERROR [expected TIMEOUT] /html/browsers/browsing-the-web/history-traversal/pageswap/pageswap-initial-navigation.html (#40387)
  • CRASH [expected OK] /html/browsers/history/the-history-interface/combination_history_001.html
  • OK [expected TIMEOUT] /html/interaction/focus/the-autofocus-attribute/update-the-rendering.html (#24145)
    • FAIL [expected TIMEOUT] subtest: "Flush autofocus candidates" should be happen before a scroll event and animation frame callbacks

      assert_array_equals: animationFrame lengths differ, expected array ["autofocus", "scroll", "animationFrame"] length 3, got ["animationFrame"] length 1
      

  • OK /html/semantics/document-metadata/the-meta-element/pragma-directives/attr-meta-http-equiv-refresh/allow-scripts-flag-changing-2.html (#39703)
    • FAIL [expected PASS] subtest: Meta refresh of the original iframe is not blocked if moved into a sandboxed iframe

      uncaught exception: Error: assert_unreached: The iframe into which the meta was moved must not refresh Reached unreachable code
      

  • TIMEOUT [expected OK] /html/semantics/embedded-content/the-iframe-element/iframe_sandbox_navigate_other_frame_popup.sub.html (#39702)
    • TIMEOUT [expected FAIL] subtest: Sandboxed iframe can not navigate other frame's popup

      Test timed out
      

  • OK /html/semantics/scripting-1/the-script-element/module/dynamic-import/blob-url.any.html (#33948)
    • FAIL [expected PASS] subtest: Revoking a blob URL immediately after calling import will not fail

      promise_test: Unhandled rejection with value: object "TypeError: Module fetching failed"
      

  • OK /html/semantics/scripting-1/the-script-element/module/dynamic-import/blob-url.any.worker.html (#33909)
    • FAIL [expected PASS] subtest: Revoking a blob URL immediately after calling import will not fail

      promise_test: Unhandled rejection with value: object "TypeError: Module fetching failed"
      

  • OK /mixed-content/tentative/autoupgrades/video-upgrade.https.sub.html (#41135)
    • FAIL [expected PASS] subtest: Video of other host autoupgraded

      assert_equals: Length. Other host expected 1 but got Infinity
      

  • OK /pointerevents/compat/pointerevent_touch_target_after_pointerdown_target_removed.tentative.html (#42813)
    • PASS [expected FAIL] subtest: After a pointerdown listener moves the target to different position, touch events should be fired on the pointerdown target, but pointer events should be fired on the pointerdown target parent
    • PASS [expected FAIL] subtest: After a pointerdown listener moves the target to different position, touchmove event should be fired on the pointerdown target parent
  • TIMEOUT [expected OK] /preload/modulepreload-sri.html (#43354)
    • TIMEOUT [expected PASS] subtest: Script should not be loaded if modulepreload's integrity is invalid

      Test timed out
      

  • OK /resource-timing/test_resource_timing.https.html (#25216)
    • PASS [expected FAIL] subtest: PerformanceEntry has correct name, initiatorType, startTime, and duration (iframe)
  • OK /touch-events/single-tap-when-touchend-listener-use-sync-xhr.html (#41175)
    • FAIL [expected PASS] subtest: Click event should be fired when touchend opens synchronous XHR

      assert_equals: expected "touchend@div, mousedown@div, mouseup@div, click@div" but got "touchend@div"
      

  • OK [expected TIMEOUT] /trusted-types/trusted-types-navigation.html?06-10 (#37920)
    • PASS [expected TIMEOUT] subtest: Navigate a frame via anchor with javascript:-urls w/ default policy in report-only mode.
    • FAIL [expected NOTRUN] subtest: Navigate a window via anchor with javascript:-urls w/ a default policy throwing an exception in enforcing mode.

      promise_test: Unhandled rejection with value: "Unexpected message received: \"No securitypolicyviolation reported!\""
      

    • FAIL [expected NOTRUN] subtest: Navigate a window via anchor with javascript:-urls w/ a default policy throwing an exception in report-only mode.

      promise_test: Unhandled rejection with value: "Unexpected message received: \"No securitypolicyviolation reported!\""
      

  • OK [expected TIMEOUT] /trusted-types/trusted-types-navigation.html?31-35 (#38034)
    • PASS [expected TIMEOUT] subtest: Navigate a frame via form-submission with javascript:-urls w/ default policy in report-only mode.
    • FAIL [expected NOTRUN] subtest: Navigate a window via form-submission with javascript:-urls w/ a default policy throwing an exception in enforcing mode.

      promise_test: Unhandled rejection with value: "Unexpected message received: \"No securitypolicyviolation reported!\""
      

    • FAIL [expected NOTRUN] subtest: Navigate a window via form-submission with javascript:-urls w/ a default policy throwing an exception in report-only mode.

      promise_test: Unhandled rejection with value: "Unexpected message received: \"No securitypolicyviolation reported!\""
      

    • FAIL [expected NOTRUN] subtest: Navigate a window via form-submission with javascript:-urls w/ a default policy making the URL invalid in enforcing mode.

      promise_test: Unhandled rejection with value: "Unexpected message received: \"No securitypolicyviolation reported!\""
      

  • OK /webdriver/tests/classic/element_click/center_point.py
    • FAIL [expected PASS] subtest: test_entirely_in_view

      webdriver.error.NoSuchWindowException: no such window (404): No such window
      

  • OK /webdriver/tests/classic/element_click/file_upload.py
    • FAIL [expected PASS] subtest: test_file_upload_state

      webdriver.error.NoSuchWindowException: no such window (404): No such window
      

  • OK /webdriver/tests/classic/execute_async_script/collections.py
    • FAIL [expected PASS] subtest: test_arguments

      AssertionError: no such window (404): No such window
      

  • OK /webdriver/tests/classic/maximize_window/maximize.py
    • ERROR [expected PASS] subtest: test_no_top_browsing_context

      setup error: webdriver.error.NoSuchWindowException: no such window (404): No such window
      

  • OK [expected TIMEOUT] /webstorage/localstorage-about-blank-3P-iframe-opens-3P-window.partitioned.html (#29053)
    • PASS [expected TIMEOUT] subtest: StorageKey: test 3P about:blank window opened from a 3P iframe
  • CRASH [expected ERROR] /workers/Worker-constructor-proto.any.serviceworker.html
Stable unexpected results that are known to be intermittent (14)
  • TIMEOUT /FileAPI/url/url-in-tags-revoke.window.html (#19978)
    • PASS [expected TIMEOUT] subtest: Fetching a blob URL immediately before revoking it works in <script> tags.
  • FAIL [expected PASS] /_mozilla/mozilla/sslfail.html (#10760)
  • TIMEOUT [expected OK] /_mozilla/mozilla/window_resize_event.html (#36741)
    • TIMEOUT [expected PASS] subtest: Popup onresize event fires after resizeTo

      Test timed out
      

  • OK /css/css-fonts/generic-family-keywords-001.html (#37467)
    • PASS [expected FAIL] subtest: @font-face matching for quoted and unquoted generic(fangsong)
    • FAIL [expected PASS] subtest: @font-face matching for quoted and unquoted generic(kai)

      assert_equals: quoted generic(kai) matches  @font-face rule expected 50 but got 30
      

  • OK /css/css-fonts/generic-family-keywords-003.html (#38994)
    • FAIL [expected PASS] subtest: @font-face matching for quoted and unquoted serif (drawing text in a canvas)

      assert_equals: quoted serif matches  @font-face rule expected 125 but got 40
      

    • FAIL [expected PASS] subtest: @font-face matching for quoted and unquoted cursive (drawing text in a canvas)

      assert_equals: quoted cursive matches  @font-face rule expected 125 but got 40
      

    • FAIL [expected PASS] subtest: @font-face matching for quoted and unquoted fantasy (drawing text in a canvas)

      assert_equals: quoted fantasy matches  @font-face rule expected 125 but got 40
      

    • FAIL [expected PASS] subtest: @font-face matching for quoted and unquoted monospace (drawing text in a canvas)

      assert_equals: quoted monospace matches  @font-face rule expected 125 but got 40
      

    • FAIL [expected PASS] subtest: @font-face matching for quoted and unquoted system-ui (drawing text in a canvas)

      assert_equals: quoted system-ui matches  @font-face rule expected 125 but got 40
      

    • FAIL [expected PASS] subtest: @font-face matching for quoted and unquoted generic(nastaliq) (drawing text in a canvas)

      assert_equals: unquoted generic(nastaliq) does not match @font-face rule expected 40 but got 125
      

    • PASS [expected FAIL] subtest: @font-face matching for quoted and unquoted ui-sans-serif (drawing text in a canvas)
  • OK /fetch/metadata/generated/css-font-face.https.sub.tentative.html (#32732)
    • PASS [expected FAIL] subtest: sec-fetch-user
  • TIMEOUT /fetch/metadata/generated/css-images.sub.tentative.html (#29047)
    • FAIL [expected PASS] subtest: content sec-fetch-site - HTTPS downgrade-upgrade

      assert_unreached: Reached unreachable code
      

  • ERROR [expected OK] /focus/focus-event-after-switching-iframes.sub.html (#40368)
  • OK /html/browsers/history/the-history-interface/traverse_the_history_5.html (#21383)
    • PASS [expected FAIL] subtest: Multiple history traversals, last would be aborted
  • CRASH [expected TIMEOUT] /html/browsers/history/the-location-interface/location_replace_session_history.html (#41896)
  • OK /html/semantics/embedded-content/media-elements/audio_loop_seek_to_eos.html (#41226)
    • PASS [expected FAIL] subtest: seeking to the end of looping audio
  • OK /preload/prefetch-document.html (#37210)
    • FAIL [expected PASS] subtest: different-site document prefetch with 'as=document' should not be consumed

      assert_equals: expected 2 but got 1
      

  • OK /resource-timing/buffer-full-add-then-clear.html (#40819)
    • FAIL [expected PASS] subtest: Test that if the buffer is cleared after entries were added to the secondary buffer, those entries make it into the primary one

      assert_equals: Number of entries does not match the expected value. expected 3 but got 0
      

  • OK /visual-viewport/resize-event-order.html (#41981)
    • PASS [expected FAIL] subtest: Popup: DOMWindow resize fired before VisualViewport.
Stable unexpected results (12)
  • OK /content-security-policy/frame-ancestors/frame-ancestors-path-ignored.window.html
    • PASS [expected FAIL] subtest: A 'frame-ancestors' CSP directive with a URL that includes a path should be ignored.
  • OK /css/css-text/i18n/ja/css-text-line-break-ja-cpm-loose.html
    • PASS [expected FAIL] subtest: 30FB KATAKANA MIDDLE DOT may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FF1A FULLWIDTH COLON may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FF1B FULLWIDTH SEMICOLON may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FF65 HALFWIDTH KATAKANA MIDDLE DOT may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 203C DOUBLE EXCLAMATION MARK may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2047 DOUBLE QUESTION MARK may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2048 QUESTION EXCLAMATION MARK may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2049 EXCLAMATION QUESTION MARK may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FF01 FULLWIDTH EXCLAMATION MARK may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FF1F FULLWIDTH QUESTION MARK may appear at line start if ja and loose
  • OK /css/css-text/i18n/ja/css-text-line-break-ja-hyphens-loose.html
    • PASS [expected FAIL] subtest: 301C WAVE DASH may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 30A0 KATAKANA-HIRAGANA DOUBLE HYPHEN may appear at line start if ja and loose
  • OK /css/css-text/i18n/ja/css-text-line-break-ja-hyphens-normal.html
    • PASS [expected FAIL] subtest: 301C WAVE DASH may appear at line start if ja and normal
    • PASS [expected FAIL] subtest: 30A0 KATAKANA-HIRAGANA DOUBLE HYPHEN may appear at line start if ja and normal
  • OK /css/css-text/i18n/ja/css-text-line-break-ja-po-loose.html
    • PASS [expected FAIL] subtest: 00B0 DEGREE SIGN may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2030 PER MILLE SIGN may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2032 PRIME may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2033 DOUBLE PRIME may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2035 REVERSED PRIME may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2103 DEGREE CELSIUS may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: 2109 DEGREE FAHRENHEIT may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FE6A SMALL PERCENT SIGN may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FF05 FULLWIDTH PERCENT SIGN may appear at line start if ja and loose
    • PASS [expected FAIL] subtest: FFE0 FULLWIDTH CENT SIGN may appear at line start if ja and loose
  • OK /css/css-text/i18n/zh/css-text-line-break-zh-cpm-loose.html
    • PASS [expected FAIL] subtest: 30FB KATAKANA MIDDLE DOT may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FF1A FULLWIDTH COLON may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FF1B FULLWIDTH SEMICOLON may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FF65 HALFWIDTH KATAKANA MIDDLE DOT may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 203C DOUBLE EXCLAMATION MARK may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2047 DOUBLE QUESTION MARK may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2048 QUESTION EXCLAMATION MARK may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2049 EXCLAMATION QUESTION MARK may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FF01 FULLWIDTH EXCLAMATION MARK may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FF1F FULLWIDTH QUESTION MARK may appear at line start if zh and loose
  • OK /css/css-text/i18n/zh/css-text-line-break-zh-hyphens-loose.html
    • PASS [expected FAIL] subtest: 301C WAVE DASH may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 30A0 KATAKANA-HIRAGANA DOUBLE HYPHEN may appear at line start if zh and loose
  • OK /css/css-text/i18n/zh/css-text-line-break-zh-hyphens-normal.html
    • PASS [expected FAIL] subtest: 301C WAVE DASH may appear at line start if zh and normal
    • PASS [expected FAIL] subtest: 30A0 KATAKANA-HIRAGANA DOUBLE HYPHEN may appear at line start if zh and normal
  • OK /css/css-text/i18n/zh/css-text-line-break-zh-po-loose.html
    • PASS [expected FAIL] subtest: 00B0 DEGREE SIGN may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2030 PER MILLE SIGN may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2032 PRIME may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2033 DOUBLE PRIME may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2035 REVERSED PRIME may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2103 DEGREE CELSIUS may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: 2109 DEGREE FAHRENHEIT may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FE6A SMALL PERCENT SIGN may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FF05 FULLWIDTH PERCENT SIGN may appear at line start if zh and loose
    • PASS [expected FAIL] subtest: FFE0 FULLWIDTH CENT SIGN may appear at line start if zh and loose
  • PASS [expected FAIL] /css/css-text/line-break/line-break-loose-013.xht
  • PASS [expected FAIL] /css/css-text/line-break/line-break-normal-013.xht
  • FAIL [expected PASS] /css/css-text/line-break/line-break-strict-013.xht

@github-actions

Copy link
Copy Markdown

⚠️ Try run (#23715380684) failed!

@TimvdLippe

Copy link
Copy Markdown
Contributor

Test results look good. You can automatically update expectations by running the following command:

./mach update-wpt https://github.com/servo/servo/actions/runs/23715380684

@xiaochengh

xiaochengh commented Mar 30, 2026

Copy link
Copy Markdown
Contributor

Are you sure this fixes #43677? I don't see how that is related to CJK.

Btw the new unit test doesn't look very helpful to me, as it's just testing the x-lang property, not anything related to line wrapping. Updating the existing test expectations will be good enough.

@SharanRP
SharanRP force-pushed the fix-43677-text-wrap-overflow branch from 80334ab to f5c70a1 Compare March 30, 2026 18:46
@SharanRP

Copy link
Copy Markdown
Contributor Author

The TPAC page uses lang="en-us" globally, so our change won't directly fix that page's overflow, but the root issue is that Servo wasn't respecting the lang attribute at all for CJK line-breaking rules. This PR fixes exactly that when content is correctly tagged with lang="ja" or lang="zh", Servo now enables the right line-breaking behavior.

@Loirooriol

Copy link
Copy Markdown
Contributor

The TPAC page uses lang="en-us" globally, so our change won't directly fix that page's overflow

If this is not fixing #43677, drop Fixes: #43677

Comment thread components/layout/flow/inline/mod.rs Outdated
// has a Japanese or Chinese language set.
options.ja_zh = {
let lang_str = lang.0.as_ref();
lang_str.starts_with("zh") || lang_str.starts_with("ja")

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Should this check that there is an hyphen after zh or ja? Even if no other language code starts with these letters, I guess an invalid one could be provided?

Or https://github.com/unicode-org/icu4x/blob/030624fc705b92bc2b8c32f68d1cc2a78cbb2fce/components/segmenter/src/line.rs#L241-L243 just checks for equality 🤔

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Ah, no, icu4x 2 checks the .language.

So maybe LanguageIdentifier::from_str(lang_str).is_ok_and(|lang_id| lang_id.language, language!("ja") | language!("zh"))?
With the idea of just using LanguageIdentifier::from_str(lang_str) once we update to icu4x 2.

@SharanRP
SharanRP force-pushed the fix-43677-text-wrap-overflow branch from f5c70a1 to f41df98 Compare April 1, 2026 20:03
@SharanRP

SharanRP commented Apr 1, 2026

Copy link
Copy Markdown
Contributor Author

starts_with wasn’t reliable, so the logic now parses the attribute using icu_locid and matches the language directly against ja and zh.

Comment thread components/layout/flow/inline/mod.rs Outdated
use icu_locid::LanguageIdentifier;
let lang_str = lang.0.as_ref();
LanguageIdentifier::from_str(lang_str).is_ok_and(|lang_id| {
let lang = lang_id.language.as_str();

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Better use the language!() macro instead of serializing and comparing as a string

@Loirooriol Loirooriol left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Comment thread components/layout/flow/inline/mod.rs Outdated
let lang = lang_id.language.as_str();
lang == "ja" || lang == "zh"
})
use icu_locid::subtags_language as language;

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Can you move the import to the start of the file? Also, I think this should work:

use icu_locid::subtags::language;

Comment thread components/layout/flow/inline/mod.rs Outdated
Comment on lines +1910 to +1912
lang.0
.as_ref()
.parse::<icu_locid::LanguageIdentifier>()

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Nit: this was a bit shorter as LanguageIdentifier::from_str(lang_str). str::parse just uses FromStr::from_str(self).

You can also import LanguageIdentifier at the start of the file.

@SharanRP
SharanRP force-pushed the fix-43677-text-wrap-overflow branch from 490e815 to 7596ee3 Compare April 2, 2026 17:17
@servo-highfive servo-highfive added the S-needs-rebase There are merge conflict errors. label Apr 2, 2026
SharanRP added 2 commits April 4, 2026 23:37
Signed-off-by: SharanRP <z8903830@gmail.com>
Signed-off-by: SharanRP <z8903830@gmail.com>
Signed-off-by: SharanRP <z8903830@gmail.com>
@SharanRP
SharanRP force-pushed the fix-43677-text-wrap-overflow branch from 7596ee3 to 95b394d Compare April 4, 2026 18:10
@servo-highfive servo-highfive removed the S-needs-rebase There are merge conflict errors. label Apr 4, 2026
Signed-off-by: SharanRP <z8903830@gmail.com>
@SharanRP
SharanRP force-pushed the fix-43677-text-wrap-overflow branch from 95b394d to f35ad25 Compare April 4, 2026 19:38
Comment thread components/layout/flow/inline/mod.rs Outdated
use icu_locid::LanguageIdentifier;
use icu_locid::subtags::language;

lang.0.as_ref().parse::<LanguageIdentifier>().is_ok_and(|lang_id| {

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

./mach fmt doesn't like this.

Suggested change
lang.0.as_ref().parse::<LanguageIdentifier>().is_ok_and(|lang_id| {
lang.0.parse::<LanguageIdentifier>().is_ok_and(|lang_id| {

Comment thread components/layout/flow/inline/mod.rs Outdated
Comment on lines +1854 to +1855
use icu_locid::LanguageIdentifier;
use icu_locid::subtags::language;

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Move to the top of the file.

Comment thread components/layout/flow/inline/mod.rs Outdated
use icu_locid::subtags::language;

lang.0.as_ref().parse::<LanguageIdentifier>().is_ok_and(|lang_id| {
lang_id.language == language!("ja") || lang_id.language == language!("zh")

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Can use matches!():

Suggested change
lang_id.language == language!("ja") || lang_id.language == language!("zh")
const JA: Language = language!("ja");
const ZH: Language = language!("zh");
matches!(lang_id.language, JA | ZH)

Signed-off-by: SharanRP <z8903830@gmail.com>
@SharanRP
SharanRP force-pushed the fix-43677-text-wrap-overflow branch from 72e760b to 6a42521 Compare April 5, 2026 11:42
@servo-highfive servo-highfive removed the S-awaiting-review There is new code that needs to be reviewed. label Apr 5, 2026
@Loirooriol

Loirooriol commented Apr 5, 2026

Copy link
Copy Markdown
Contributor

Also adds a small unit test to lock in the behavior.

I don't see such thing, editing out

@Loirooriol Loirooriol changed the title Fix CJK text wrapping overflow layout: Fix line breaking opportunities for Chinese and Japanese Apr 5, 2026
@Loirooriol
Loirooriol added this pull request to the merge queue Apr 5, 2026
@servo-highfive servo-highfive added the S-awaiting-merge The PR is in the process of compiling and running tests on the automated CI. label Apr 5, 2026
Merged via the queue into servo:main with commit 57b86ed Apr 5, 2026
32 checks passed
@servo-highfive servo-highfive removed the S-awaiting-merge The PR is in the process of compiling and running tests on the automated CI. label Apr 5, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants