Title: [265487] trunk
Revision
265487
Author
mmaxfi...@apple.com
Date
2020-08-10 21:23:51 -0700 (Mon, 10 Aug 2020)

Log Message

[Cocoa] Migrate from CTFontTransformGlyphsWithLanguage() to CTFontShapeGlyphs()
https://bugs.webkit.org/show_bug.cgi?id=215059

Reviewed by Darin Adler.

Source/WebCore:

This is in preparation for https://bugs.webkit.org/show_bug.cgi?id=214769
and https://bugs.webkit.org/show_bug.cgi?id=206208.

The solution for https://bugs.webkit.org/show_bug.cgi?id=214769 requires applying
letter-spacing after text shaping. Today, we apply letter-spacing before text shaping
which is wrong. However, if we want to apply letter-spacing after text shaping, we need
to use CTFontShapeGlyphs(), which returns the glyph -> string mapping, which allows us
to determine which glyphs to add letter-spacing to.

Updates existing tests.

Tests: fast/text/international/kana-voiced-sound-marks-1.html
       fast/text/international/kana-voiced-sound-marks-2.html

* platform/graphics/Font.cpp:
(WebCore::Font::applyTransforms const):
* platform/graphics/Font.h:
* platform/graphics/FontCascade.cpp:
(WebCore::FontCascade::widthForSimpleText const):
(WebCore::FontCascade::characterRangeCodePath):
(WebCore::FontCascade::layoutSimpleText const):
* platform/graphics/FontCascade.h:
* platform/graphics/SurrogatePairAwareTextIterator.cpp:
(WebCore::SurrogatePairAwareTextIterator::consumeSlowCase): Now that we're using
CTFontShapeGlyphs(), the shaping routine can and does look at the underlying character
string to perform character composition. This means that the glyph buffer needs to
match exactly what is in the string. We can't do any shenanigans where we pretend the
string has characters that aren't actually there.
* platform/graphics/SurrogatePairAwareTextIterator.h:
(WebCore::SurrogatePairAwareTextIterator::consume):
* platform/graphics/WidthIterator.cpp:
(WebCore::WidthIterator::shouldApplyFontTransforms const):
(WebCore::WidthIterator::applyFontTransforms): Reversing the glyph buffer for rtl
content needs to be done inside platform-specific code, because its behavior depends on
which platform shaping routine is being used.
(WebCore::WidthIterator::commitCurrentFontRange):
(WebCore::WidthIterator::advanceInternal):
* platform/graphics/WidthIterator.h:
* platform/graphics/cocoa/FontCocoa.mm:
(WebCore::Font::applyTransforms const):
* platform/graphics/mac/SimpleFontDataCoreText.cpp:
(WebCore::Font::getCFStringAttributes const):

Source/WebCore/PAL:

* pal/spi/cocoa/CoreTextSPI.h:

Source/WTF:

* wtf/PlatformUse.h: Rename CTFONTTRANSFORMGLYPHSWITHLANGUAGE to CTFONTSHAPEGLYPHS,
because that's the new function.

LayoutTests:

* fast/encoding/denormalised-voiced-japanese-chars-expected.html: Copied from LayoutTests/fast/encoding/denormalised-voiced-japanese-chars.html.
* fast/encoding/denormalised-voiced-japanese-chars.html: Update to be a reftest.
* fast/text/international/kana-voiced-sound-marks-1-expected.html: Copied from LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks-expected.html.
Make the test more robust.
* fast/text/international/kana-voiced-sound-marks-1.html: Renamed from LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks.html.
Make the test more robust.
* fast/text/international/kana-voiced-sound-marks-2-expected.html: Copied from LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks-expected.html.
Make the test more robust.
* fast/text/international/kana-voiced-sound-marks-2.html: Renamed from LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks-expected.html.
Make the test more robust.
* fast/text/soft-hyphen-min-preferred-width-expected.html:
* fast/text/soft-hyphen-min-preferred-width.html: Update to be more robust.
* platform/gtk/fast/encoding/denormalised-voiced-japanese-chars-expected.png: Removed.
* platform/gtk/fast/encoding/denormalised-voiced-japanese-chars-expected.txt: Removed.
* platform/ios/fast/encoding/denormalised-voiced-japanese-chars-expected.txt: Removed.
* platform/mac-bigsur/svg/W3C-I18N/tspan-direction-rtl-expected.txt: Added Big Sur -expected result.
* platform/mac-bigsur/svg/text/bidi-tspans-expected.txt: Ditto.
* platform/mac/fast/encoding/denormalised-voiced-japanese-chars-expected.png: Removed.
* platform/mac/fast/encoding/denormalised-voiced-japanese-chars-expected.txt: Removed.
* platform/win/fast/encoding/denormalised-voiced-japanese-chars-expected.txt: Removed.
* platform/wincairo/fast/encoding/denormalised-voiced-japanese-chars-expected.txt: Removed.
* platform/wpe/fast/encoding/denormalised-voiced-japanese-chars-expected.txt: Removed.

Modified Paths

Added Paths

Removed Paths

Diff

Modified: trunk/LayoutTests/ChangeLog (265486 => 265487)


--- trunk/LayoutTests/ChangeLog	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/LayoutTests/ChangeLog	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,3 +1,33 @@
+2020-08-10  Myles C. Maxfield  <mmaxfi...@apple.com>
+
+        [Cocoa] Migrate from CTFontTransformGlyphsWithLanguage() to CTFontShapeGlyphs()
+        https://bugs.webkit.org/show_bug.cgi?id=215059
+
+        Reviewed by Darin Adler.
+
+        * fast/encoding/denormalised-voiced-japanese-chars-expected.html: Copied from LayoutTests/fast/encoding/denormalised-voiced-japanese-chars.html.
+        * fast/encoding/denormalised-voiced-japanese-chars.html: Update to be a reftest.
+        * fast/text/international/kana-voiced-sound-marks-1-expected.html: Copied from LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks-expected.html.
+        Make the test more robust.
+        * fast/text/international/kana-voiced-sound-marks-1.html: Renamed from LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks.html.
+        Make the test more robust.
+        * fast/text/international/kana-voiced-sound-marks-2-expected.html: Copied from LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks-expected.html.
+        Make the test more robust.
+        * fast/text/international/kana-voiced-sound-marks-2.html: Renamed from LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks-expected.html.
+        Make the test more robust.
+        * fast/text/soft-hyphen-min-preferred-width-expected.html:
+        * fast/text/soft-hyphen-min-preferred-width.html: Update to be more robust.
+        * platform/gtk/fast/encoding/denormalised-voiced-japanese-chars-expected.png: Removed.
+        * platform/gtk/fast/encoding/denormalised-voiced-japanese-chars-expected.txt: Removed.
+        * platform/ios/fast/encoding/denormalised-voiced-japanese-chars-expected.txt: Removed.
+        * platform/mac-bigsur/svg/W3C-I18N/tspan-direction-rtl-expected.txt: Added Big Sur -expected result.
+        * platform/mac-bigsur/svg/text/bidi-tspans-expected.txt: Ditto.
+        * platform/mac/fast/encoding/denormalised-voiced-japanese-chars-expected.png: Removed.
+        * platform/mac/fast/encoding/denormalised-voiced-japanese-chars-expected.txt: Removed.
+        * platform/win/fast/encoding/denormalised-voiced-japanese-chars-expected.txt: Removed.
+        * platform/wincairo/fast/encoding/denormalised-voiced-japanese-chars-expected.txt: Removed.
+        * platform/wpe/fast/encoding/denormalised-voiced-japanese-chars-expected.txt: Removed.
+
 2020-08-10  Lauro Moura  <lmo...@igalia.com>
 
         [GTK][WPE] Gardening failures and rebaseline some tests.

Copied: trunk/LayoutTests/fast/encoding/denormalised-voiced-japanese-chars-expected.html (from rev 265486, trunk/LayoutTests/fast/encoding/denormalised-voiced-japanese-chars.html) (0 => 265487)


--- trunk/LayoutTests/fast/encoding/denormalised-voiced-japanese-chars-expected.html	                        (rev 0)
+++ trunk/LayoutTests/fast/encoding/denormalised-voiced-japanese-chars-expected.html	2020-08-11 04:23:51 UTC (rev 265487)
@@ -0,0 +1,11 @@
+<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
+<head>
+<meta http-equiv="content-type" content="text/html; charset=UTF-8" />
+</head>
+<body>
+This test checks that the decomposed unicode version of voiced japanese hiragana and katakana characters are rendered the same as the precomposed version.
+<h2 style="font-family: 'Hiragino Mincho ProN';">バナナとパナマ</h2>
+
+</body>
+</html>

Modified: trunk/LayoutTests/fast/encoding/denormalised-voiced-japanese-chars.html (265486 => 265487)


--- trunk/LayoutTests/fast/encoding/denormalised-voiced-japanese-chars.html	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/LayoutTests/fast/encoding/denormalised-voiced-japanese-chars.html	2020-08-11 04:23:51 UTC (rev 265487)
@@ -4,12 +4,8 @@
 <meta http-equiv="content-type" content="text/html; charset=UTF-8" />
 </head>
 <body>
-This test checks that the decomposed unicode version of voiced japanese hiragana and katakana characters are rendered the same as the precomposed version. This test is a pixel-test, and passes when the text in the two heading elements are identical.
-<h2>バナナとパナマ</h2>
-<p>The above is decomposed</p>
+This test checks that the decomposed unicode version of voiced japanese hiragana and katakana characters are rendered the same as the precomposed version.
+<h2 style="font-family: 'Hiragino Mincho ProN';">バナナとパナマ</h2>
 
-<h2>バナナとパナマ</h2>
-<p>The above is precomposed</p>
-
 </body>
 </html>

Copied: trunk/LayoutTests/fast/text/international/kana-voiced-sound-marks-1-expected.html (from rev 265486, trunk/LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks-expected.html) (0 => 265487)


--- trunk/LayoutTests/fast/text/international/kana-voiced-sound-marks-1-expected.html	                        (rev 0)
+++ trunk/LayoutTests/fast/text/international/kana-voiced-sound-marks-1-expected.html	2020-08-11 04:23:51 UTC (rev 265487)
@@ -0,0 +1,21 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<style>
+.test {
+  border:solid 1px;
+  display:inline-block;
+  font-family:"Hiragino Kaku Gothic Pro","MS Gothic";
+  font-size:25px;
+}
+</style>
+<div>
+<p>Test passes if two blocks are identical.
+<div class=test>
+<div>ばび</div>
+<div>ぱぴ</div>
+</div>
+<div class=test>
+<div>ばび</div>
+<div>ぱぴ</div>
+</div>
+</div>

Copied: trunk/LayoutTests/fast/text/international/kana-voiced-sound-marks-1.html (from rev 265486, trunk/LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks.html) (0 => 265487)


--- trunk/LayoutTests/fast/text/international/kana-voiced-sound-marks-1.html	                        (rev 0)
+++ trunk/LayoutTests/fast/text/international/kana-voiced-sound-marks-1.html	2020-08-11 04:23:51 UTC (rev 265487)
@@ -0,0 +1,21 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<style>
+.test {
+  border:solid 1px;
+  display:inline-block;
+  font-family:"Hiragino Kaku Gothic Pro","MS Gothic";
+  font-size:25px;
+}
+</style>
+<div>
+<p>Test passes if two blocks are identical.
+<div class=test>
+<div>は&#x3099;ひ&#x3099;</div>
+<div>は&#x309A;ひ&#x309A;</div>
+</div>
+<div class=test>
+<div>ばび</div>
+<div>ぱぴ</div>
+</div>
+</div>

Copied: trunk/LayoutTests/fast/text/international/kana-voiced-sound-marks-2-expected.html (from rev 265486, trunk/LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks-expected.html) (0 => 265487)


--- trunk/LayoutTests/fast/text/international/kana-voiced-sound-marks-2-expected.html	                        (rev 0)
+++ trunk/LayoutTests/fast/text/international/kana-voiced-sound-marks-2-expected.html	2020-08-11 04:23:51 UTC (rev 265487)
@@ -0,0 +1,21 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<style>
+.test {
+  border:solid 1px;
+  display:inline-block;
+  font-family:"Hiragino Kaku Gothic Pro","MS Gothic";
+  font-size:25px;
+}
+</style>
+<div>
+<p>Test passes if two blocks are identical.
+<div class=test>
+<div>ぶべぼ</div>
+<div>ぷぺぽ</div>
+</div>
+<div class=test>
+<div>ぶべぼ</div>
+<div>ぷぺぽ</div>
+</div>
+</div>

Copied: trunk/LayoutTests/fast/text/international/kana-voiced-sound-marks-2.html (from rev 265486, trunk/LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks-expected.html) (0 => 265487)


--- trunk/LayoutTests/fast/text/international/kana-voiced-sound-marks-2.html	                        (rev 0)
+++ trunk/LayoutTests/fast/text/international/kana-voiced-sound-marks-2.html	2020-08-11 04:23:51 UTC (rev 265487)
@@ -0,0 +1,21 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<style>
+.test {
+  border:solid 1px;
+  display:inline-block;
+  font-family:"Hiragino Kaku Gothic Pro","MS Gothic";
+  font-size:25px;
+}
+</style>
+<div>
+<p>Test passes if two blocks are identical.
+<div class=test>
+<div>ふ&#x3099;へ&#x3099;ほ&#x3099;</div>
+<div>ふ&#x309A;へ&#x309A;ほ&#x309A;</div>
+</div>
+<div class=test>
+<div>ぶべぼ</div>
+<div>ぷぺぽ</div>
+</div>
+</div>

Modified: trunk/LayoutTests/fast/text/soft-hyphen-min-preferred-width-expected.html (265486 => 265487)


--- trunk/LayoutTests/fast/text/soft-hyphen-min-preferred-width-expected.html	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/LayoutTests/fast/text/soft-hyphen-min-preferred-width-expected.html	2020-08-11 04:23:51 UTC (rev 265487)
@@ -11,7 +11,7 @@
 <table cellspacing=0 cellpadding=0>
     <tr>
         <td>
-            <div>extraordinar<span>-</span><br>ily</div>
+            <div>extraordina-<br>rily</div>
         </td>
         <td style="width: 100%"></td>
     </tr>

Modified: trunk/LayoutTests/fast/text/soft-hyphen-min-preferred-width.html (265486 => 265487)


--- trunk/LayoutTests/fast/text/soft-hyphen-min-preferred-width.html	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/LayoutTests/fast/text/soft-hyphen-min-preferred-width.html	2020-08-11 04:23:51 UTC (rev 265487)
@@ -11,7 +11,7 @@
 <table cellspacing=0 cellpadding=0>
     <tr>
         <td>
-            <div style="-webkit-hyphens: manual;">extraordinar&shy;ily</div>
+            <div style="-webkit-hyphens: manual;">extraordina&shy;rily</div>
         </td>
         <td style="width: 100%"></td>
     </tr>

Deleted: trunk/LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks-expected.html (265486 => 265487)


--- trunk/LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks-expected.html	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks-expected.html	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,21 +0,0 @@
-<!DOCTYPE html>
-<meta charset="utf-8">
-<style>
-.test {
-  border:solid 1px;
-  display:inline-block;
-  font-family:"Hiragino Kaku Gothic Pro","MS Gothic";
-  font-size:25px;
-}
-</style>
-<div>
-<p>Test passes if two blocks are identical.
-<div class=test>
-<div>ばびぶべぼ</div>
-<div>ぱぴぷぺぽ</div>
-</div>
-<div class=test>
-<div>ばびぶべぼ</div>
-<div>ぱぴぷぺぽ</div>
-</div>
-</div>

Deleted: trunk/LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks.html (265486 => 265487)


--- trunk/LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks.html	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/LayoutTests/imported/blink/fast/text/international/kana-voiced-sound-marks.html	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,21 +0,0 @@
-<!DOCTYPE html>
-<meta charset="utf-8">
-<style>
-.test {
-  border:solid 1px;
-  display:inline-block;
-  font-family:"Hiragino Kaku Gothic Pro","MS Gothic";
-  font-size:25px;
-}
-</style>
-<div>
-<p>Test passes if two blocks are identical.
-<div class=test>
-<div>は&#x3099;ひ&#x3099;ふ&#x3099;へ&#x3099;ほ&#x3099;</div>
-<div>は&#x309A;ひ&#x309A;ふ&#x309A;へ&#x309A;ほ&#x309A;</div>
-</div>
-<div class=test>
-<div>ばびぶべぼ</div>
-<div>ぱぴぷぺぽ</div>
-</div>
-</div>

Deleted: trunk/LayoutTests/platform/gtk/fast/encoding/denormalised-voiced-japanese-chars-expected.png


(Binary files differ)

Deleted: trunk/LayoutTests/platform/gtk/fast/encoding/denormalised-voiced-japanese-chars-expected.txt (265486 => 265487)


--- trunk/LayoutTests/platform/gtk/fast/encoding/denormalised-voiced-japanese-chars-expected.txt	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/LayoutTests/platform/gtk/fast/encoding/denormalised-voiced-japanese-chars-expected.txt	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,22 +0,0 @@
-layer at (0,0) size 800x600
-  RenderView at (0,0) size 800x600
-layer at (0,0) size 800x248
-  RenderBlock {HTML} at (0,0) size 800x248
-    RenderBody {BODY} at (8,8) size 784x224
-      RenderBlock (anonymous) at (0,0) size 784x54
-        RenderText {#text} at (0,0) size 775x53
-          text run at (0,0) width 775: "This test checks that the decomposed unicode version of voiced japanese hiragana and katakana characters are rendered the"
-          text run at (0,18) width 724: "same as the precomposed version. This test is a pixel-test, and passes when the text in the two heading elements are"
-          text run at (0,36) width 57: "identical."
-      RenderBlock {H2} at (0,73) size 784x28
-        RenderText {#text} at (0,0) size 175x26
-          text run at (0,0) width 175: "\x{30CF}\x{3099}\x{30CA}\x{30CA}\x{3068}\x{30CF}\x{309A}\x{30CA}\x{30DE}"
-      RenderBlock {P} at (0,120) size 784x19
-        RenderText {#text} at (0,0) size 164x17
-          text run at (0,0) width 164: "The above is decomposed"
-      RenderBlock {H2} at (0,158) size 784x28
-        RenderText {#text} at (0,0) size 175x26
-          text run at (0,0) width 175: "\x{30D0}\x{30CA}\x{30CA}\x{3068}\x{30D1}\x{30CA}\x{30DE}"
-      RenderBlock {P} at (0,205) size 784x19
-        RenderText {#text} at (0,0) size 169x17
-          text run at (0,0) width 169: "The above is precomposed"

Deleted: trunk/LayoutTests/platform/ios/fast/encoding/denormalised-voiced-japanese-chars-expected.txt (265486 => 265487)


--- trunk/LayoutTests/platform/ios/fast/encoding/denormalised-voiced-japanese-chars-expected.txt	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/LayoutTests/platform/ios/fast/encoding/denormalised-voiced-japanese-chars-expected.txt	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,22 +0,0 @@
-layer at (0,0) size 800x600
-  RenderView at (0,0) size 800x600
-layer at (0,0) size 800x264
-  RenderBlock {HTML} at (0,0) size 800x264
-    RenderBody {BODY} at (8,8) size 784x240
-      RenderBlock (anonymous) at (0,0) size 784x60
-        RenderText {#text} at (0,0) size 766x59
-          text run at (0,0) width 766: "This test checks that the decomposed unicode version of voiced japanese hiragana and katakana characters are rendered"
-          text run at (0,20) width 763: "the same as the precomposed version. This test is a pixel-test, and passes when the text in the two heading elements are"
-          text run at (0,40) width 60: "identical."
-      RenderBlock {H2} at (0,79) size 784x31
-        RenderText {#text} at (0,1) size 168x28
-          text run at (0,1) width 168: "\x{30CF}\x{3099}\x{30CA}\x{30CA}\x{3068}\x{30CF}\x{309A}\x{30CA}\x{30DE}"
-      RenderBlock {P} at (0,129) size 784x21
-        RenderText {#text} at (0,0) size 166x19
-          text run at (0,0) width 166: "The above is decomposed"
-      RenderBlock {H2} at (0,169) size 784x31
-        RenderText {#text} at (0,1) size 168x28
-          text run at (0,1) width 168: "\x{30D0}\x{30CA}\x{30CA}\x{3068}\x{30D1}\x{30CA}\x{30DE}"
-      RenderBlock {P} at (0,219) size 784x21
-        RenderText {#text} at (0,0) size 172x19
-          text run at (0,0) width 172: "The above is precomposed"

Deleted: trunk/LayoutTests/platform/mac/fast/encoding/denormalised-voiced-japanese-chars-expected.png


(Binary files differ)

Deleted: trunk/LayoutTests/platform/mac/fast/encoding/denormalised-voiced-japanese-chars-expected.txt (265486 => 265487)


--- trunk/LayoutTests/platform/mac/fast/encoding/denormalised-voiced-japanese-chars-expected.txt	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/LayoutTests/platform/mac/fast/encoding/denormalised-voiced-japanese-chars-expected.txt	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,22 +0,0 @@
-layer at (0,0) size 800x600
-  RenderView at (0,0) size 800x600
-layer at (0,0) size 800x260
-  RenderBlock {HTML} at (0,0) size 800x260
-    RenderBody {BODY} at (8,8) size 784x236
-      RenderBlock (anonymous) at (0,0) size 784x54
-        RenderText {#text} at (0,0) size 766x54
-          text run at (0,0) width 766: "This test checks that the decomposed unicode version of voiced japanese hiragana and katakana characters are rendered"
-          text run at (0,18) width 763: "the same as the precomposed version. This test is a pixel-test, and passes when the text in the two heading elements are"
-          text run at (0,36) width 60: "identical."
-      RenderBlock {H2} at (0,73) size 784x34
-        RenderText {#text} at (0,3) size 168x28
-          text run at (0,3) width 168: "\x{30CF}\x{3099}\x{30CA}\x{30CA}\x{3068}\x{30CF}\x{309A}\x{30CA}\x{30DE}"
-      RenderBlock {P} at (0,126) size 784x19
-        RenderText {#text} at (0,0) size 166x18
-          text run at (0,0) width 166: "The above is decomposed"
-      RenderBlock {H2} at (0,164) size 784x34
-        RenderText {#text} at (0,3) size 168x28
-          text run at (0,3) width 168: "\x{30D0}\x{30CA}\x{30CA}\x{3068}\x{30D1}\x{30CA}\x{30DE}"
-      RenderBlock {P} at (0,217) size 784x19
-        RenderText {#text} at (0,0) size 172x18
-          text run at (0,0) width 172: "The above is precomposed"

Added: trunk/LayoutTests/platform/mac-bigsur/svg/W3C-I18N/tspan-direction-rtl-expected.txt (0 => 265487)


--- trunk/LayoutTests/platform/mac-bigsur/svg/W3C-I18N/tspan-direction-rtl-expected.txt	                        (rev 0)
+++ trunk/LayoutTests/platform/mac-bigsur/svg/W3C-I18N/tspan-direction-rtl-expected.txt	2020-08-11 04:23:51 UTC (rev 265487)
@@ -0,0 +1,28 @@
+layer at (0,0) size 800x600
+  RenderView at (0,0) size 800x600
+layer at (0,0) size 800x600
+  RenderSVGRoot {svg} at (0,0) size 800x600
+    RenderSVGContainer {g} at (33,222) size 651x143
+      RenderSVGText {text} at (92,133) size 276x21 contains 1 chunk(s)
+        RenderSVGInlineText {#text} at (191,0) size 85x21
+          chunk 1 (middle anchor) text run 1 at (283.65,150.00) startOffset 0 endOffset 14 width 84.15 RTL: "\x{646}\x{634}\x{627}\x{637} \x{627}\x{644}\x{62A}\x{62F}\x{648}\x{64A}\x{644} \""
+        RenderSVGTSpan {tspan} at (0,0) size 181x21
+          RenderSVGInlineText {#text} at (11,0) size 181x21
+            chunk 1 (middle anchor) text run 1 at (103.60,150.00) startOffset 0 endOffset 8 width 44.98 RTL: ", \x{627}\x{62E}\x{62A}\x{628}\x{627}\x{631}"
+            chunk 1 (middle anchor) text run 1 at (148.58,150.00) startOffset 0 endOffset 14 width 135.07: "dirRTL ubEmbed"
+        RenderSVGInlineText {#text} at (0,0) size 12x21
+          chunk 1 (middle anchor) text run 1 at (92.21,150.00) startOffset 0 endOffset 2 width 11.39 RTL: "\"!"
+      RenderSVGText {text} at (20,170) size 87x13 contains 1 chunk(s)
+        RenderSVGInlineText {#text} at (0,0) size 87x12
+          chunk 1 text run 1 at (20.00,180.00) startOffset 0 endOffset 18 width 86.18: "Reference graphic:"
+      RenderSVGImage {image} at (100,300) size 584x65
+    RenderSVGContainer {g} at (16,557) size 73x12
+      RenderSVGText {text} at (10,334) size 44x8 contains 1 chunk(s)
+        RenderSVGInlineText {#text} at (0,0) size 44x7
+          chunk 1 text run 1 at (10.00,340.00) startOffset 0 endOffset 16 width 43.03: "$Revision: 1.7 $"
+    RenderSVGRect {rect} at (0,0) size 800x600 [stroke={[type=SOLID] [color=#000000]}] [x=1.00] [y=1.00] [width=478.00] [height=358.00]
+    RenderSVGContainer {g} at (0,0) size 800x38
+      RenderSVGRect {rect} at (0,0) size 800x36 [stroke={[type=SOLID] [color=#000000]}] [fill={[type=SOLID] [color=#FF0000]}] [x=1.00] [y=1.00] [width=478.00] [height=20.00]
+      RenderSVGText {text} at (206,0) size 68x23 contains 1 chunk(s)
+        RenderSVGInlineText {#text} at (0,0) size 68x23
+          chunk 1 (middle anchor) text run 1 at (206.46,18.00) startOffset 0 endOffset 5 width 67.09: "DRAFT"
Property changes on: trunk/LayoutTests/platform/mac-bigsur/svg/W3C-I18N/tspan-direction-rtl-expected.txt
___________________________________________________________________

Added: svn:eol-style

+native \ No newline at end of property

Added: svn:keywords

+Author Date Id Rev URL \ No newline at end of property

Added: trunk/LayoutTests/platform/mac-bigsur/svg/text/bidi-tspans-expected.txt (0 => 265487)


--- trunk/LayoutTests/platform/mac-bigsur/svg/text/bidi-tspans-expected.txt	                        (rev 0)
+++ trunk/LayoutTests/platform/mac-bigsur/svg/text/bidi-tspans-expected.txt	2020-08-11 04:23:51 UTC (rev 265487)
@@ -0,0 +1,19 @@
+layer at (0,0) size 800x600
+  RenderView at (0,0) size 800x600
+layer at (0,0) size 800x600
+  RenderSVGRoot {svg} at (153,222) size 460x85
+    RenderSVGContainer {g} at (153,222) size 460x85
+      RenderSVGText {text} at (92,133) size 276x21 contains 1 chunk(s)
+        RenderSVGInlineText {#text} at (0,0) size 276x21
+          chunk 1 (middle anchor) text run 1 at (92.21,150.00) startOffset 0 endOffset 10 width 56.37 RTL: ", \x{627}\x{62E}\x{62A}\x{628}\x{627}\x{631}\"!"
+          chunk 1 (middle anchor) text run 1 at (148.58,150.00) startOffset 0 endOffset 14 width 135.07: "dirRTL ubEmbed"
+          chunk 1 (middle anchor) text run 1 at (283.65,150.00) startOffset 0 endOffset 14 width 84.15 RTL: "\x{646}\x{634}\x{627}\x{637} \x{627}\x{644}\x{62A}\x{62F}\x{648}\x{64A}\x{644} \""
+      RenderSVGText {text} at (92,163) size 276x21 contains 1 chunk(s)
+        RenderSVGInlineText {#text} at (191,0) size 85x21
+          chunk 1 (middle anchor) text run 1 at (283.65,180.00) startOffset 0 endOffset 14 width 84.15 RTL: "\x{646}\x{634}\x{627}\x{637} \x{627}\x{644}\x{62A}\x{62F}\x{648}\x{64A}\x{644} \""
+        RenderSVGTSpan {tspan} at (0,0) size 181x21
+          RenderSVGInlineText {#text} at (11,0) size 181x21
+            chunk 1 (middle anchor) text run 1 at (103.60,180.00) startOffset 0 endOffset 8 width 44.98 RTL: ", \x{627}\x{62E}\x{62A}\x{628}\x{627}\x{631}"
+            chunk 1 (middle anchor) text run 1 at (148.58,180.00) startOffset 0 endOffset 14 width 135.07: "dirRTL ubEmbed"
+        RenderSVGInlineText {#text} at (0,0) size 12x21
+          chunk 1 (middle anchor) text run 1 at (92.21,180.00) startOffset 0 endOffset 2 width 11.39 RTL: "\"!"
Property changes on: trunk/LayoutTests/platform/mac-bigsur/svg/text/bidi-tspans-expected.txt
___________________________________________________________________

Added: svn:eol-style

+native \ No newline at end of property

Added: svn:keywords

+Author Date Id Rev URL \ No newline at end of property

Deleted: trunk/LayoutTests/platform/win/fast/encoding/denormalised-voiced-japanese-chars-expected.txt (265486 => 265487)


--- trunk/LayoutTests/platform/win/fast/encoding/denormalised-voiced-japanese-chars-expected.txt	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/LayoutTests/platform/win/fast/encoding/denormalised-voiced-japanese-chars-expected.txt	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,22 +0,0 @@
-layer at (0,0) size 800x600
-  RenderView at (0,0) size 800x600
-layer at (0,0) size 800x266
-  RenderBlock {HTML} at (0,0) size 800x266
-    RenderBody {BODY} at (8,8) size 784x242
-      RenderBlock (anonymous) at (0,0) size 784x54
-        RenderText {#text} at (0,0) size 775x54
-          text run at (0,0) width 775: "This test checks that the decomposed unicode version of voiced japanese hiragana and katakana characters are rendered the"
-          text run at (0,18) width 724: "same as the precomposed version. This test is a pixel-test, and passes when the text in the two heading elements are"
-          text run at (0,36) width 57: "identical."
-      RenderBlock {H2} at (0,73) size 784x37
-        RenderText {#text} at (0,5) size 168x28
-          text run at (0,5) width 168: "\x{30CF}\x{3099}\x{30CA}\x{30CA}\x{3068}\x{30CF}\x{309A}\x{30CA}\x{30DE}"
-      RenderBlock {P} at (0,129) size 784x19
-        RenderText {#text} at (0,0) size 164x18
-          text run at (0,0) width 164: "The above is decomposed"
-      RenderBlock {H2} at (0,167) size 784x37
-        RenderText {#text} at (0,5) size 168x28
-          text run at (0,5) width 168: "\x{30D0}\x{30CA}\x{30CA}\x{3068}\x{30D1}\x{30CA}\x{30DE}"
-      RenderBlock {P} at (0,223) size 784x19
-        RenderText {#text} at (0,0) size 169x18
-          text run at (0,0) width 169: "The above is precomposed"

Deleted: trunk/LayoutTests/platform/wincairo/fast/encoding/denormalised-voiced-japanese-chars-expected.txt (265486 => 265487)


--- trunk/LayoutTests/platform/wincairo/fast/encoding/denormalised-voiced-japanese-chars-expected.txt	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/LayoutTests/platform/wincairo/fast/encoding/denormalised-voiced-japanese-chars-expected.txt	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,21 +0,0 @@
-layer at (0,0) size 800x600
-  RenderView at (0,0) size 800x600
-layer at (0,0) size 800x238
-  RenderBlock {HTML} at (0,0) size 800x238
-    RenderBody {BODY} at (8,8) size 784x214
-      RenderBlock (anonymous) at (0,0) size 784x40
-        RenderText {#text} at (0,0) size 784x39
-          text run at (0,0) width 784: "This test checks that the decomposed unicode version of voiced japanese hiragana and katakana characters are rendered the same"
-          text run at (0,20) width 717: "as the precomposed version. This test is a pixel-test, and passes when the text in the two heading elements are identical."
-      RenderBlock {H2} at (0,59) size 784x28
-        RenderText {#text} at (0,0) size 164x26
-          text run at (0,0) width 164: "\x{30CF}\x{3099}\x{30CA}\x{30CA}\x{3068}\x{30CF}\x{309A}\x{30CA}\x{30DE}"
-      RenderBlock {P} at (0,106) size 784x21
-        RenderText {#text} at (0,0) size 159x19
-          text run at (0,0) width 159: "The above is decomposed"
-      RenderBlock {H2} at (0,146) size 784x28
-        RenderText {#text} at (0,0) size 164x26
-          text run at (0,0) width 164: "\x{30D0}\x{30CA}\x{30CA}\x{3068}\x{30D1}\x{30CA}\x{30DE}"
-      RenderBlock {P} at (0,193) size 784x21
-        RenderText {#text} at (0,0) size 164x19
-          text run at (0,0) width 164: "The above is precomposed"

Deleted: trunk/LayoutTests/platform/wpe/fast/encoding/denormalised-voiced-japanese-chars-expected.txt (265486 => 265487)


--- trunk/LayoutTests/platform/wpe/fast/encoding/denormalised-voiced-japanese-chars-expected.txt	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/LayoutTests/platform/wpe/fast/encoding/denormalised-voiced-japanese-chars-expected.txt	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,22 +0,0 @@
-layer at (0,0) size 800x600
-  RenderView at (0,0) size 800x600
-layer at (0,0) size 800x248
-  RenderBlock {HTML} at (0,0) size 800x248
-    RenderBody {BODY} at (8,8) size 784x224
-      RenderBlock (anonymous) at (0,0) size 784x54
-        RenderText {#text} at (0,0) size 775x53
-          text run at (0,0) width 775: "This test checks that the decomposed unicode version of voiced japanese hiragana and katakana characters are rendered the"
-          text run at (0,18) width 724: "same as the precomposed version. This test is a pixel-test, and passes when the text in the two heading elements are"
-          text run at (0,36) width 57: "identical."
-      RenderBlock {H2} at (0,73) size 784x28
-        RenderText {#text} at (0,0) size 168x26
-          text run at (0,0) width 168: "\x{30CF}\x{3099}\x{30CA}\x{30CA}\x{3068}\x{30CF}\x{309A}\x{30CA}\x{30DE}"
-      RenderBlock {P} at (0,120) size 784x19
-        RenderText {#text} at (0,0) size 164x17
-          text run at (0,0) width 164: "The above is decomposed"
-      RenderBlock {H2} at (0,158) size 784x28
-        RenderText {#text} at (0,0) size 168x26
-          text run at (0,0) width 168: "\x{30D0}\x{30CA}\x{30CA}\x{3068}\x{30D1}\x{30CA}\x{30DE}"
-      RenderBlock {P} at (0,205) size 784x19
-        RenderText {#text} at (0,0) size 169x17
-          text run at (0,0) width 169: "The above is precomposed"

Modified: trunk/Source/WTF/ChangeLog (265486 => 265487)


--- trunk/Source/WTF/ChangeLog	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WTF/ChangeLog	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,3 +1,13 @@
+2020-08-10  Myles C. Maxfield  <mmaxfi...@apple.com>
+
+        [Cocoa] Migrate from CTFontTransformGlyphsWithLanguage() to CTFontShapeGlyphs()
+        https://bugs.webkit.org/show_bug.cgi?id=215059
+
+        Reviewed by Darin Adler.
+
+        * wtf/PlatformUse.h: Rename CTFONTTRANSFORMGLYPHSWITHLANGUAGE to CTFONTSHAPEGLYPHS,
+        because that's the new function.
+
 2020-08-09  Ben Nham  <n...@apple.com>
 
         Preload graphics drivers in Mac WebProcess

Modified: trunk/Source/WTF/wtf/PlatformUse.h (265486 => 265487)


--- trunk/Source/WTF/wtf/PlatformUse.h	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WTF/wtf/PlatformUse.h	2020-08-11 04:23:51 UTC (rev 265487)
@@ -302,5 +302,5 @@
 #endif
 
 #if PLATFORM(COCOA) && !(PLATFORM(MAC) && __MAC_OS_X_VERSION_MIN_REQUIRED < 110000)
-#define USE_CTFONTTRANSFORMGLYPHSWITHLANGUAGE 1
+#define USE_CTFONTSHAPEGLYPHS 1
 #endif

Modified: trunk/Source/WebCore/ChangeLog (265486 => 265487)


--- trunk/Source/WebCore/ChangeLog	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/ChangeLog	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,3 +1,53 @@
+2020-08-10  Myles C. Maxfield  <mmaxfi...@apple.com>
+
+        [Cocoa] Migrate from CTFontTransformGlyphsWithLanguage() to CTFontShapeGlyphs()
+        https://bugs.webkit.org/show_bug.cgi?id=215059
+
+        Reviewed by Darin Adler.
+
+        This is in preparation for https://bugs.webkit.org/show_bug.cgi?id=214769
+        and https://bugs.webkit.org/show_bug.cgi?id=206208.
+
+        The solution for https://bugs.webkit.org/show_bug.cgi?id=214769 requires applying
+        letter-spacing after text shaping. Today, we apply letter-spacing before text shaping
+        which is wrong. However, if we want to apply letter-spacing after text shaping, we need
+        to use CTFontShapeGlyphs(), which returns the glyph -> string mapping, which allows us
+        to determine which glyphs to add letter-spacing to.
+
+        Updates existing tests.
+
+        Tests: fast/text/international/kana-voiced-sound-marks-1.html
+               fast/text/international/kana-voiced-sound-marks-2.html
+
+        * platform/graphics/Font.cpp:
+        (WebCore::Font::applyTransforms const):
+        * platform/graphics/Font.h:
+        * platform/graphics/FontCascade.cpp:
+        (WebCore::FontCascade::widthForSimpleText const):
+        (WebCore::FontCascade::characterRangeCodePath):
+        (WebCore::FontCascade::layoutSimpleText const):
+        * platform/graphics/FontCascade.h:
+        * platform/graphics/SurrogatePairAwareTextIterator.cpp:
+        (WebCore::SurrogatePairAwareTextIterator::consumeSlowCase): Now that we're using
+        CTFontShapeGlyphs(), the shaping routine can and does look at the underlying character
+        string to perform character composition. This means that the glyph buffer needs to
+        match exactly what is in the string. We can't do any shenanigans where we pretend the
+        string has characters that aren't actually there.
+        * platform/graphics/SurrogatePairAwareTextIterator.h:
+        (WebCore::SurrogatePairAwareTextIterator::consume):
+        * platform/graphics/WidthIterator.cpp:
+        (WebCore::WidthIterator::shouldApplyFontTransforms const):
+        (WebCore::WidthIterator::applyFontTransforms): Reversing the glyph buffer for rtl
+        content needs to be done inside platform-specific code, because its behavior depends on
+        which platform shaping routine is being used.
+        (WebCore::WidthIterator::commitCurrentFontRange):
+        (WebCore::WidthIterator::advanceInternal):
+        * platform/graphics/WidthIterator.h:
+        * platform/graphics/cocoa/FontCocoa.mm:
+        (WebCore::Font::applyTransforms const):
+        * platform/graphics/mac/SimpleFontDataCoreText.cpp:
+        (WebCore::Font::getCFStringAttributes const):
+
 2020-08-10  Devin Rousso  <drou...@apple.com>
 
         Add quirk to force touch events on mail.yahoo.com

Modified: trunk/Source/WebCore/PAL/ChangeLog (265486 => 265487)


--- trunk/Source/WebCore/PAL/ChangeLog	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/PAL/ChangeLog	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,3 +1,12 @@
+2020-08-10  Myles C. Maxfield  <mmaxfi...@apple.com>
+
+        [Cocoa] Migrate from CTFontTransformGlyphsWithLanguage() to CTFontShapeGlyphs()
+        https://bugs.webkit.org/show_bug.cgi?id=215059
+
+        Reviewed by Darin Adler.
+
+        * pal/spi/cocoa/CoreTextSPI.h:
+
 2020-08-07  John Wilander  <wilan...@apple.com>
 
         Experimental: Cap the expiry of persistent cookies set in 3rd-party CNAME cloaked HTTP responses

Modified: trunk/Source/WebCore/PAL/pal/spi/cocoa/CoreTextSPI.h (265486 => 265487)


--- trunk/Source/WebCore/PAL/pal/spi/cocoa/CoreTextSPI.h	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/PAL/pal/spi/cocoa/CoreTextSPI.h	2020-08-11 04:23:51 UTC (rev 265487)
@@ -46,6 +46,12 @@
     kCTFontTransformApplyPositioning = (1 << 1)
 };
 
+typedef CF_OPTIONS(CFOptionFlags, CTFontShapeOptions) {
+    kCTFontShapeWithKerning = (1 << 0),
+    kCTFontShapeWithClusterComposition = (1 << 1),
+    kCTFontShapeRightToLeft = (1 << 2),
+};
+
 typedef CF_OPTIONS(uint32_t, CTFontDescriptorOptions) {
     kCTFontDescriptorOptionSystemUIFont = 1 << 1,
     kCTFontDescriptorOptionPreferAppleSystemFont = kCTFontOptionsPreferSystemFont
@@ -92,7 +98,7 @@
 extern const CFStringRef kCTFontCSSFamilySystemUI;
 
 bool CTFontTransformGlyphs(CTFontRef, CGGlyph glyphs[], CGSize advances[], CFIndex count, CTFontTransformOptions);
-CGSize CTFontTransformGlyphsWithLanguage(CTFontRef, CGGlyph[], CGSize[], CFIndex count, CTFontTransformOptions, CFStringRef language, void (^handler)(CFRange, CGGlyph**, CGSize**));
+CGSize CTFontShapeGlyphs(CTFontRef, CGGlyph glyphs[], CGSize advances[], CGPoint origins[], CFIndex indexes[], const UniChar chars[], CFIndex count, CTFontShapeOptions, CFStringRef language, void (^handler)(CFRange, CGGlyph**, CGSize**, CGPoint**, CFIndex**));
 
 CGSize CTRunGetInitialAdvance(CTRunRef);
 CTLineRef CTLineCreateWithUniCharProvider(CTUniCharProviderCallback, CTUniCharDisposeCallback, void* refCon);

Modified: trunk/Source/WebCore/platform/graphics/Font.cpp (265486 => 265487)


--- trunk/Source/WebCore/platform/graphics/Font.cpp	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/platform/graphics/Font.cpp	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2005, 2008, 2010, 2015 Apple Inc. All rights reserved.
+ * Copyright (C) 2005-2020 Apple Inc. All rights reserved.
  * Copyright (C) 2006 Alexey Proskuryakov
  *
  * Redistribution and use in source and binary forms, with or without
@@ -512,7 +512,7 @@
 }
 
 #if !PLATFORM(COCOA)
-void Font::applyTransforms(GlyphBuffer&, unsigned, bool, bool, const AtomString&) const
+void Font::applyTransforms(GlyphBuffer&, unsigned, unsigned, bool, bool, const AtomString&, StringView, TextDirection) const
 {
 }
 #endif

Modified: trunk/Source/WebCore/platform/graphics/Font.h (265486 => 265487)


--- trunk/Source/WebCore/platform/graphics/Font.h	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/platform/graphics/Font.h	2020-08-11 04:23:51 UTC (rev 265487)
@@ -1,7 +1,7 @@
 /*
  * This file is part of the internal font implementation.
  *
- * Copyright (C) 2006, 2008, 2010, 2015-2016 Apple Inc. All rights reserved.
+ * Copyright (C) 2006-2020 Apple Inc. All rights reserved.
  * Copyright (C) 2007-2008 Torch Mobile, Inc.
  *
  * This library is free software; you can redistribute it and/or
@@ -207,7 +207,7 @@
 #endif
 
     bool canRenderCombiningCharacterSequence(const UChar*, size_t) const;
-    void applyTransforms(GlyphBuffer&, unsigned beginningIndex, bool enableKerning, bool requiresShaping, const AtomString& locale) const;
+    void applyTransforms(GlyphBuffer&, unsigned beginningGlyphIndex, unsigned beginningStringIndex, bool enableKerning, bool requiresShaping, const AtomString& locale, StringView text, TextDirection) const;
 
 #if PLATFORM(WIN)
     SCRIPT_FONTPROPERTIES* scriptFontProperties() const;

Modified: trunk/Source/WebCore/platform/graphics/FontCascade.cpp (265486 => 265487)


--- trunk/Source/WebCore/platform/graphics/FontCascade.cpp	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/platform/graphics/FontCascade.cpp	2020-08-11 04:23:51 UTC (rev 265487)
@@ -426,7 +426,7 @@
     return result;
 }
 
-float FontCascade::widthForSimpleText(StringView text) const
+float FontCascade::widthForSimpleText(StringView text, TextDirection textDirection) const
 {
     if (text.isNull() || text.isEmpty())
         return 0;
@@ -445,7 +445,7 @@
         glyphBuffer.add(glyph, font, glyphWidth, i);
     }
 
-    font.applyTransforms(glyphBuffer, 0, enableKerning(), requiresShaping(), fontDescription().computedLocale());
+    font.applyTransforms(glyphBuffer, 0, 0, enableKerning(), requiresShaping(), fontDescription().computedLocale(), text, textDirection);
     // This is needed only to match the result of the slow path.
     // Same glyph widths but different floating point arithmetic can produce different run width.
     float runWidthDifferenceWithTransformApplied = -runWidth;
@@ -748,6 +748,11 @@
         if (c <= 0x302F)
             return Complex;
 
+        if (c < 0x3099)
+            continue;
+        if (c < 0x309D)
+            return Complex; // KATAKANA-HIRAGANA (SEMI-)VOICED SOUND MARKS require character composition
+
         if (c < 0xA67C) // U+A67C through U+A67D Combining marks for old Cyrillic
             continue;
         if (c <= 0xA67D)
@@ -1391,6 +1396,8 @@
     // FIXME: Deal with the GlyphBuffer's current initialAdvance.
     glyphBuffer.setInitialAdvance(FloatSize(initialAdvance, 0));
 
+    // The glyph buffer is currently in logical order,
+    // but we need to return the results in visual order.
     if (run.rtl())
         glyphBuffer.reverse(0, glyphBuffer.size());
 

Modified: trunk/Source/WebCore/platform/graphics/FontCascade.h (265486 => 265487)


--- trunk/Source/WebCore/platform/graphics/FontCascade.h	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/platform/graphics/FontCascade.h	2020-08-11 04:23:51 UTC (rev 265487)
@@ -116,7 +116,7 @@
 
     float widthOfTextRange(const TextRun&, unsigned from, unsigned to, HashSet<const Font*>* fallbackFonts = 0, float* outWidthBeforeRange = nullptr, float* outWidthAfterRange = nullptr) const;
     WEBCORE_EXPORT float width(const TextRun&, HashSet<const Font*>* fallbackFonts = 0, GlyphOverflow* = 0) const;
-    float widthForSimpleText(StringView text) const;
+    float widthForSimpleText(StringView text, TextDirection = TextDirection::LTR) const;
 
     std::unique_ptr<TextLayout, TextLayoutDeleter> createLayout(RenderText&, float xPos, bool collapseWhiteSpace) const;
     static float width(TextLayout&, unsigned from, unsigned len, HashSet<const Font*>* fallbackFonts = 0);

Modified: trunk/Source/WebCore/platform/graphics/SurrogatePairAwareTextIterator.cpp (265486 => 265487)


--- trunk/Source/WebCore/platform/graphics/SurrogatePairAwareTextIterator.cpp	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/platform/graphics/SurrogatePairAwareTextIterator.cpp	2020-08-11 04:23:51 UTC (rev 265487)
@@ -37,20 +37,8 @@
 
 bool SurrogatePairAwareTextIterator::consumeSlowCase(UChar32& character, unsigned& clusterLength)
 {
-    if (character <= 0x30FE) {
-        // Deal with Hiragana and Katakana voiced and semi-voiced syllables.
-        // Normalize into composed form, and then look for glyph with base + combined mark.
-        // Check above for character range to minimize performance impact.
-        if (UChar32 normalized = normalizeVoicingMarks()) {
-            character = normalized;
-            clusterLength = 2;
-        }
-        return true;
-    }
+    ASSERT(U16_IS_SURROGATE(character));
 
-    if (!U16_IS_SURROGATE(character))
-        return true;
-
     // If we have a surrogate pair, make sure it starts with the high part.
     if (!U16_IS_SURROGATE_LEAD(character))
         return false;

Modified: trunk/Source/WebCore/platform/graphics/SurrogatePairAwareTextIterator.h (265486 => 265487)


--- trunk/Source/WebCore/platform/graphics/SurrogatePairAwareTextIterator.h	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/platform/graphics/SurrogatePairAwareTextIterator.h	2020-08-11 04:23:51 UTC (rev 265487)
@@ -40,7 +40,7 @@
         character = *m_characters;
         clusterLength = 1;
 
-        if (character < HiraganaLetterSmallA)
+        if (!U16_IS_SURROGATE(character))
             return true;
 
         return consumeSlowCase(character, clusterLength);

Modified: trunk/Source/WebCore/platform/graphics/WidthIterator.cpp (265486 => 265487)


--- trunk/Source/WebCore/platform/graphics/WidthIterator.cpp	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/platform/graphics/WidthIterator.cpp	2020-08-11 04:23:51 UTC (rev 265487)
@@ -78,9 +78,10 @@
     return codepoint >= 0xE001 && codepoint <= 0xE537;
 }
 
-inline auto WidthIterator::shouldApplyFontTransforms(const GlyphBuffer& glyphBuffer, unsigned lastGlyphCount, UChar32 previousCharacter) const -> TransformsType
+inline auto WidthIterator::shouldApplyFontTransforms(const GlyphBuffer& glyphBuffer, unsigned lastGlyphCount, unsigned currentCharacterIndex) const -> TransformsType
 {
-    if (glyphBuffer.size() == (lastGlyphCount + 1) && isSoftBankEmoji(previousCharacter))
+    ASSERT(currentCharacterIndex <= m_run.length());
+    if (glyphBuffer.size() == (lastGlyphCount + 1) && currentCharacterIndex && isSoftBankEmoji(m_run.text()[currentCharacterIndex - 1]))
         return TransformsType::Forced;
     if (m_run.length() <= 1)
         return TransformsType::None;
@@ -87,15 +88,13 @@
     return TransformsType::NotForced;
 }
 
-inline float WidthIterator::applyFontTransforms(GlyphBuffer& glyphBuffer, bool ltr, unsigned& lastGlyphCount, const Font& font, UChar32 previousCharacter, bool force, CharactersTreatedAsSpace& charactersTreatedAsSpace)
+inline float WidthIterator::applyFontTransforms(GlyphBuffer& glyphBuffer, unsigned lastGlyphCount, unsigned currentCharacterIndex, const Font& font, bool force, CharactersTreatedAsSpace& charactersTreatedAsSpace)
 {
-    ASSERT_UNUSED(previousCharacter, shouldApplyFontTransforms(glyphBuffer, lastGlyphCount, previousCharacter) != WidthIterator::TransformsType::None);
+    ASSERT_UNUSED(currentCharacterIndex, shouldApplyFontTransforms(glyphBuffer, lastGlyphCount, currentCharacterIndex) != WidthIterator::TransformsType::None);
 
     auto glyphBufferSize = glyphBuffer.size();
-    if (!force && glyphBufferSize <= lastGlyphCount + 1) {
-        lastGlyphCount = glyphBufferSize;
+    if (!force && glyphBufferSize <= lastGlyphCount + 1)
         return 0;
-    }
 
     GlyphBufferAdvance* advances = glyphBuffer.advances(0);
     float beforeWidth = 0;
@@ -103,18 +102,16 @@
         beforeWidth += advances[i].width();
 
     ASSERT(lastGlyphCount <= glyphBufferSize);
-    if (!ltr)
-        glyphBuffer.reverse(lastGlyphCount, glyphBufferSize - lastGlyphCount);
 
-    font.applyTransforms(glyphBuffer, lastGlyphCount, m_enableKerning, m_requiresShaping, m_font.fontDescription().computedLocale());
+    font.applyTransforms(glyphBuffer, lastGlyphCount, m_currentCharacterIndex, m_enableKerning, m_requiresShaping, m_font.fontDescription().computedLocale(), m_run.text(), m_run.direction());
     glyphBufferSize = glyphBuffer.size();
 
-    for (unsigned i = lastGlyphCount; i < glyphBufferSize; ++i)
+    GlyphBufferOrigin* origins = glyphBuffer.origins(0);
+    for (unsigned i = lastGlyphCount; i < glyphBufferSize; ++i) {
         advances[i].setHeight(-advances[i].height());
+        origins[i].setY(-origins[i].y());
+    }
 
-    if (!ltr)
-        glyphBuffer.reverse(lastGlyphCount, glyphBufferSize - lastGlyphCount);
-
     for (unsigned i = lastGlyphCount; i < glyphBufferSize; ++i) {
         auto characterIndex = glyphBuffer.stringOffsetAt(i);
         auto iterator = std::lower_bound(charactersTreatedAsSpace.begin(), charactersTreatedAsSpace.end(), characterIndex, [](const OriginalAdvancesForCharacterTreatedAsSpace& l, GlyphBufferStringOffset r) -> bool {
@@ -133,7 +130,6 @@
     for (unsigned i = lastGlyphCount; i < glyphBufferSize; ++i)
         afterWidth += advances[i].width();
 
-    lastGlyphCount = glyphBufferSize;
     return afterWidth - beforeWidth;
 }
 
@@ -166,11 +162,12 @@
     return std::make_pair(expandLeft, expandRight);
 }
 
-void WidthIterator::commitCurrentFontRange(GlyphBuffer& glyphBuffer, unsigned lastGlyphCount, const Font& font, UChar32 previousCharacter, const Font& primaryFont, UChar32 character, float widthOfCurrentFontRange, CharactersTreatedAsSpace& charactersTreatedAsSpace)
+void WidthIterator::commitCurrentFontRange(GlyphBuffer& glyphBuffer, unsigned lastGlyphCount, unsigned currentCharacterIndex, const Font& font, const Font& primaryFont, UChar32 character, float widthOfCurrentFontRange, CharactersTreatedAsSpace& charactersTreatedAsSpace)
 {
-    auto transformsType = shouldApplyFontTransforms(glyphBuffer, lastGlyphCount, previousCharacter);
+    auto transformsType = shouldApplyFontTransforms(glyphBuffer, lastGlyphCount, currentCharacterIndex);
     if (transformsType != TransformsType::None)
-        m_runWidthSoFar += applyFontTransforms(glyphBuffer, m_run.ltr(), lastGlyphCount, font, previousCharacter, transformsType == TransformsType::Forced, charactersTreatedAsSpace);
+        m_runWidthSoFar += applyFontTransforms(glyphBuffer, lastGlyphCount, currentCharacterIndex, font, transformsType == TransformsType::Forced, charactersTreatedAsSpace);
+    m_currentCharacterIndex = currentCharacterIndex;
 
     if (widthOfCurrentFontRange && m_fallbackFonts && &font != &primaryFont) {
         // FIXME: This does a little extra work that could be avoided if
@@ -188,7 +185,7 @@
 template <typename TextIterator>
 inline void WidthIterator::advanceInternal(TextIterator& textIterator, GlyphBuffer& glyphBuffer)
 {
-    // The core logic here needs to match SimpleLineLayout::widthForSimpleText()
+    // The core logic here needs to match FontCascade::widthForSimpleText()
     bool rtl = m_run.rtl();
     bool hasExtraSpacing = (m_font.letterSpacing() || m_font.wordSpacing() || m_expansion) && !m_run.spacingDisabled();
 
@@ -204,8 +201,8 @@
     const Font* lastFontData = &primaryFont;
     unsigned lastGlyphCount = glyphBuffer.size();
 
+    auto currentCharacterIndex = textIterator.currentIndex();
     UChar32 character = 0;
-    UChar32 previousCharacter = 0;
     unsigned clusterLength = 0;
     CharactersTreatedAsSpace charactersTreatedAsSpace;
     float widthOfCurrentFontRange = 0;
@@ -218,14 +215,15 @@
         // doesn't support the code point. We should ignore them at this point to ensure they are not displayed.
         if (!characterMustDrawSomething) {
             textIterator.advance(advanceLength);
+            currentCharacterIndex = textIterator.currentIndex();
             continue;
         }
 #endif
-        int currentCharacterIndex = textIterator.currentIndex();
         const GlyphData& glyphData = m_font.glyphDataForCharacter(character, rtl);
         Glyph glyph = glyphData.glyph;
         if (!glyph && !characterMustDrawSomething) {
             textIterator.advance(advanceLength);
+            currentCharacterIndex = textIterator.currentIndex();
             continue;
         }
         const Font* font = glyphData.font ? glyphData.font : &m_font.primaryFont();
@@ -243,8 +241,7 @@
         }
 
         if (font != lastFontData) {
-            commitCurrentFontRange(glyphBuffer, lastGlyphCount, *lastFontData, previousCharacter, primaryFont, character, widthOfCurrentFontRange, charactersTreatedAsSpace);
-            m_currentCharacterIndex = currentCharacterIndex;
+            commitCurrentFontRange(glyphBuffer, lastGlyphCount, currentCharacterIndex, *lastFontData, primaryFont, character, widthOfCurrentFontRange, charactersTreatedAsSpace);
             lastGlyphCount = glyphBuffer.size();
             lastFontData = font;
             widthOfCurrentFontRange = width;
@@ -289,6 +286,8 @@
                                     glyphBuffer.add(font->zeroWidthSpaceGlyph(), *font, m_expansionPerOpportunity, currentCharacterIndex);
                                 else
                                     glyphBuffer.add(font->spaceGlyph(), *font, m_expansionPerOpportunity, currentCharacterIndex);
+                                lastGlyphCount = glyphBuffer.size();
+                                m_currentCharacterIndex = currentCharacterIndex;
                             } else
                                 glyphBuffer.expandLastAdvance(m_expansionPerOpportunity);
                         } else {
@@ -314,7 +313,7 @@
                 m_isAfterExpansion = false;
         }
 
-        auto transformsType = shouldApplyFontTransforms(glyphBuffer, lastGlyphCount, previousCharacter);
+        auto transformsType = shouldApplyFontTransforms(glyphBuffer, lastGlyphCount, currentCharacterIndex);
         if (transformsType != TransformsType::None && FontCascade::treatAsSpace(character)) {
             charactersTreatedAsSpace.constructAndAppend(
                 currentCharacterIndex,
@@ -332,23 +331,22 @@
         if (m_forTextEmphasis && !FontCascade::canReceiveTextEmphasis(character))
             glyph = 0;
 
+        glyphBuffer.add(glyph, *font, width, currentCharacterIndex);
+
         // Advance past the character we just dealt with.
         textIterator.advance(advanceLength);
+        currentCharacterIndex = textIterator.currentIndex();
 
         m_runWidthSoFar += width;
 
-        glyphBuffer.add(glyph, *font, width, currentCharacterIndex);
-
         if (m_accountForGlyphBounds) {
             m_maxGlyphBoundingBoxY = std::max(m_maxGlyphBoundingBoxY, bounds.maxY());
             m_minGlyphBoundingBoxY = std::min(m_minGlyphBoundingBoxY, bounds.y());
             m_lastGlyphOverflow = std::max<float>(0, bounds.maxX() - width);
         }
-        previousCharacter = character;
     }
 
-    commitCurrentFontRange(glyphBuffer, lastGlyphCount, *lastFontData, previousCharacter, primaryFont, character, widthOfCurrentFontRange, charactersTreatedAsSpace);
-    m_currentCharacterIndex = textIterator.currentIndex();
+    commitCurrentFontRange(glyphBuffer, lastGlyphCount, currentCharacterIndex, *lastFontData, primaryFont, character, widthOfCurrentFontRange, charactersTreatedAsSpace);
 
     if (leftoverJustificationWidth) {
         if (m_forTextEmphasis)

Modified: trunk/Source/WebCore/platform/graphics/WidthIterator.h (265486 => 265487)


--- trunk/Source/WebCore/platform/graphics/WidthIterator.h	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/platform/graphics/WidthIterator.h	2020-08-11 04:23:51 UTC (rev 265487)
@@ -60,9 +60,9 @@
     inline void advanceInternal(TextIterator&, GlyphBuffer&);
 
     enum class TransformsType { None, Forced, NotForced };
-    TransformsType shouldApplyFontTransforms(const GlyphBuffer&, unsigned lastGlyphCount, UChar32 previousCharacter) const;
-    float applyFontTransforms(GlyphBuffer&, bool ltr, unsigned& lastGlyphCount, const Font&, UChar32 previousCharacter, bool force, CharactersTreatedAsSpace&);
-    void commitCurrentFontRange(GlyphBuffer&, unsigned lastGlyphCount, const Font&, UChar32 previousCharacter, const Font& primaryFont, UChar32 character, float widthOfCurrentFontRange, CharactersTreatedAsSpace&);
+    TransformsType shouldApplyFontTransforms(const GlyphBuffer&, unsigned lastGlyphCount, unsigned currentCharacterIndex) const;
+    float applyFontTransforms(GlyphBuffer&, unsigned lastGlyphCount, unsigned currentCharacterIndex, const Font&, bool force, CharactersTreatedAsSpace&);
+    void commitCurrentFontRange(GlyphBuffer&, unsigned lastGlyphCount, unsigned currentCharacterIndex, const Font&, const Font& primaryFont, UChar32 character, float widthOfCurrentFontRange, CharactersTreatedAsSpace&);
 
     const FontCascade& m_font;
     const TextRun& m_run;

Modified: trunk/Source/WebCore/platform/graphics/cocoa/FontCocoa.mm (265486 => 265487)


--- trunk/Source/WebCore/platform/graphics/cocoa/FontCocoa.mm	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/platform/graphics/cocoa/FontCocoa.mm	2020-08-11 04:23:51 UTC (rev 265487)
@@ -544,28 +544,78 @@
     return createDerivativeFont(scaledFont.get(), size, m_platformData.orientation(), fontTraits, m_platformData.syntheticBold(), m_platformData.syntheticOblique());
 }
 
-void Font::applyTransforms(GlyphBuffer& glyphBuffer, unsigned beginningIndex, bool enableKerning, bool requiresShaping, const AtomString& locale) const
+void Font::applyTransforms(GlyphBuffer& glyphBuffer, unsigned beginningGlyphIndex, unsigned beginningStringIndex, bool enableKerning, bool requiresShaping, const AtomString& locale, StringView text, TextDirection textDirection) const
 {
+    UNUSED_PARAM(requiresShaping);
+
     // FIXME: Implement GlyphBuffer initial advance.
-    UNUSED_PARAM(requiresShaping);
-    CTFontTransformOptions options = (enableKerning ? kCTFontTransformApplyPositioning : 0) | kCTFontTransformApplyShaping;
-#if USE(CTFONTTRANSFORMGLYPHSWITHLANGUAGE)
-    auto handler = ^(CFRange range, CGGlyph** newGlyphsPointer, CGSize** newAdvancesPointer) {
+#if USE(CTFONTSHAPEGLYPHS)
+    auto handler = ^(CFRange range, CGGlyph** newGlyphsPointer, CGSize** newAdvancesPointer, CGPoint** newOffsetsPointer, CFIndex** newIndicesPointer) {
         range.location = std::min(std::max(range.location, static_cast<CFIndex>(0)), static_cast<CFIndex>(glyphBuffer.size()));
         if (range.length < 0) {
             range.length = std::min(range.location, -range.length);
             range.location = range.location - range.length;
-            glyphBuffer.remove(beginningIndex + range.location, range.length);
+            glyphBuffer.remove(beginningGlyphIndex + range.location, range.length);
         } else
-            glyphBuffer.makeHole(beginningIndex + range.location, range.length, this);
-        *newGlyphsPointer = glyphBuffer.glyphs(beginningIndex);
-        *newAdvancesPointer = glyphBuffer.advances(beginningIndex);
+            glyphBuffer.makeHole(beginningGlyphIndex + range.location, range.length, this);
+
+        *newGlyphsPointer = glyphBuffer.glyphs(beginningGlyphIndex);
+        *newAdvancesPointer = glyphBuffer.advances(beginningGlyphIndex);
+        *newOffsetsPointer = glyphBuffer.origins(beginningGlyphIndex);
+        *newIndicesPointer = glyphBuffer.offsetsInString(beginningGlyphIndex);
     };
-    CTFontTransformGlyphsWithLanguage(m_platformData.ctFont(), glyphBuffer.glyphs(beginningIndex), reinterpret_cast<CGSize*>(glyphBuffer.advances(beginningIndex)), glyphBuffer.size() - beginningIndex, options, LocaleCocoa::canonicalLanguageIdentifierFromString(locale).string().createCFString().get(), handler);
+
+    auto substring = text.substring(beginningStringIndex);
+    auto upconvertedCharacters = substring.upconvertedCharacters();
+    auto localeString = LocaleCocoa::canonicalLanguageIdentifierFromString(locale).string().createCFString();
+    CTFontShapeOptions options = kCTFontShapeWithClusterComposition
+        | (enableKerning ? kCTFontShapeWithKerning : 0)
+        | (textDirection == TextDirection::RTL ? kCTFontShapeRightToLeft : 0);
+
+    for (unsigned i = 0; i < glyphBuffer.size() - beginningGlyphIndex; ++i)
+        glyphBuffer.offsetsInString(beginningGlyphIndex)[i] -= beginningStringIndex;
+
+    CTFontShapeGlyphs(
+        m_platformData.ctFont(),
+        glyphBuffer.glyphs(beginningGlyphIndex),
+        reinterpret_cast<CGSize*>(glyphBuffer.advances(beginningGlyphIndex)),
+        reinterpret_cast<CGPoint*>(glyphBuffer.origins(beginningGlyphIndex)),
+        glyphBuffer.offsetsInString(beginningGlyphIndex),
+        reinterpret_cast<const UniChar*>(upconvertedCharacters.get()),
+        glyphBuffer.size() - beginningGlyphIndex,
+        options,
+        localeString.get(),
+        handler);
+
+    for (unsigned i = 0; i < glyphBuffer.size() - beginningGlyphIndex; ++i)
+        glyphBuffer.offsetsInString(beginningGlyphIndex)[i] += beginningStringIndex;
+
 #else
+
+    UNUSED_PARAM(beginningStringIndex);
     UNUSED_PARAM(locale);
-    CTFontTransformGlyphs(m_platformData.ctFont(), glyphBuffer.glyphs(beginningIndex), reinterpret_cast<CGSize*>(glyphBuffer.advances(beginningIndex)), glyphBuffer.size() - beginningIndex, options);
+    UNUSED_PARAM(text);
+
+    // CTFontTransformGlyphs() operates in visual order, but WidthIterator iterates in logical order.
+    // Temporarily put us in visual order just for the call, then put us back into logical order when
+    // the call is done.
+    // We don't have a global view of the entire GlyphBuffer; we're just operating on a single chunk of it.
+    // WidthIterator encounters the chunks out in logical order, so we have to maintain that invariant.
+    // Eventually, FontCascade::layoutSimpleText() will reverse the whole buffer to put the entire thing
+    // in visual order, but that's okay because it has a view of the entire GlyphBuffer.
+    // On the other hand, CTFontShapeGlyphs() accepts the buffer in logical order but returns it in physical
+    // order, which means the second reverse() in this function still needs to execute when
+    // CTFontShapeGlyphs() is being used.
+    if (textDirection == TextDirection::RTL)
+        glyphBuffer.reverse(beginningGlyphIndex, glyphBuffer.size() - beginningGlyphIndex);
+
+    CTFontTransformOptions options = (enableKerning ? kCTFontTransformApplyPositioning : 0) | kCTFontTransformApplyShaping;
+    CTFontTransformGlyphs(m_platformData.ctFont(), glyphBuffer.glyphs(beginningGlyphIndex), reinterpret_cast<CGSize*>(glyphBuffer.advances(beginningGlyphIndex)), glyphBuffer.size() - beginningGlyphIndex, options);
 #endif
+
+    // See the comment above in this function where the other call to reverse() is.
+    if (textDirection == TextDirection::RTL)
+        glyphBuffer.reverse(beginningGlyphIndex, glyphBuffer.size() - beginningGlyphIndex);
 }
 
 static int extractNumber(CFNumberRef number)

Modified: trunk/Source/WebCore/platform/graphics/mac/SimpleFontDataCoreText.cpp (265486 => 265487)


--- trunk/Source/WebCore/platform/graphics/mac/SimpleFontDataCoreText.cpp	2020-08-11 03:52:43 UTC (rev 265486)
+++ trunk/Source/WebCore/platform/graphics/mac/SimpleFontDataCoreText.cpp	2020-08-11 04:23:51 UTC (rev 265487)
@@ -41,7 +41,7 @@
     values[0] = platformData().ctFont();
     size_t count = 1;
 
-#if USE(CTFONTTRANSFORMGLYPHSWITHLANGUAGE)
+#if USE(CTFONTSHAPEGLYPHS)
     RetainPtr<CFStringRef> localeString;
     if (!locale.isEmpty()) {
         localeString = locale.string().createCFString();
_______________________________________________
webkit-changes mailing list
webkit-changes@lists.webkit.org
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to