<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><meta http-equiv="content-type" content="text/html; charset=utf-8" />
<title>[278107] branches/safari-612.1.15.4-branch</title>
</head>
<body>

<style type="text/css"><!--
#msg dl.meta { border: 1px #006 solid; background: #369; padding: 6px; color: #fff; }
#msg dl.meta dt { float: left; width: 6em; font-weight: bold; }
#msg dt:after { content:':';}
#msg dl, #msg dt, #msg ul, #msg li, #header, #footer, #logmsg { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt;  }
#msg dl a { font-weight: bold}
#msg dl a:link    { color:#fc3; }
#msg dl a:active  { color:#ff0; }
#msg dl a:visited { color:#cc6; }
h3 { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; font-weight: bold; }
#msg pre { overflow: auto; background: #ffc; border: 1px #fa0 solid; padding: 6px; }
#logmsg { background: #ffc; border: 1px #fa0 solid; padding: 1em 1em 0 1em; }
#logmsg p, #logmsg pre, #logmsg blockquote { margin: 0 0 1em 0; }
#logmsg p, #logmsg li, #logmsg dt, #logmsg dd { line-height: 14pt; }
#logmsg h1, #logmsg h2, #logmsg h3, #logmsg h4, #logmsg h5, #logmsg h6 { margin: .5em 0; }
#logmsg h1:first-child, #logmsg h2:first-child, #logmsg h3:first-child, #logmsg h4:first-child, #logmsg h5:first-child, #logmsg h6:first-child { margin-top: 0; }
#logmsg ul, #logmsg ol { padding: 0; list-style-position: inside; margin: 0 0 0 1em; }
#logmsg ul { text-indent: -1em; padding-left: 1em; }#logmsg ol { text-indent: -1.5em; padding-left: 1.5em; }
#logmsg > ul, #logmsg > ol { margin: 0 0 1em 0; }
#logmsg pre { background: #eee; padding: 1em; }
#logmsg blockquote { border: 1px solid #fa0; border-left-width: 10px; padding: 1em 1em 0 1em; background: white;}
#logmsg dl { margin: 0; }
#logmsg dt { font-weight: bold; }
#logmsg dd { margin: 0; padding: 0 0 0.5em 0; }
#logmsg dd:before { content:'\00bb';}
#logmsg table { border-spacing: 0px; border-collapse: collapse; border-top: 4px solid #fa0; border-bottom: 1px solid #fa0; background: #fff; }
#logmsg table th { text-align: left; font-weight: normal; padding: 0.2em 0.5em; border-top: 1px dotted #fa0; }
#logmsg table td { text-align: right; border-top: 1px dotted #fa0; padding: 0.2em 0.5em; }
#logmsg table thead th { text-align: center; border-bottom: 1px solid #fa0; }
#logmsg table th.Corner { text-align: left; }
#logmsg hr { border: none 0; border-top: 2px dashed #fa0; height: 1px; }
#header, #footer { color: #fff; background: #636; border: 1px #300 solid; padding: 6px; }
#patch { width: 100%; }
#patch h4 {font-family: verdana,arial,helvetica,sans-serif;font-size:10pt;padding:8px;background:#369;color:#fff;margin:0;}
#patch .propset h4, #patch .binary h4 {margin:0;}
#patch pre {padding:0;line-height:1.2em;margin:0;}
#patch .diff {width:100%;background:#eee;padding: 0 0 10px 0;overflow:auto;}
#patch .propset .diff, #patch .binary .diff  {padding:10px 0;}
#patch span {display:block;padding:0 10px;}
#patch .modfile, #patch .addfile, #patch .delfile, #patch .propset, #patch .binary, #patch .copfile {border:1px solid #ccc;margin:10px 0;}
#patch ins {background:#dfd;text-decoration:none;display:block;padding:0 10px;}
#patch del {background:#fdd;text-decoration:none;display:block;padding:0 10px;}
#patch .lines, .info {color:#888;background:#fff;}
--></style>
<div id="msg">
<dl class="meta">
<dt>Revision</dt> <dd><a href="http://trac.webkit.org/projects/webkit/changeset/278107">278107</a></dd>
<dt>Author</dt> <dd>repstein@apple.com</dd>
<dt>Date</dt> <dd>2021-05-26 11:48:15 -0700 (Wed, 26 May 2021)</dd>
</dl>

<h3>Log Message</h3>
<pre>Cherry-pick <a href="http://trac.webkit.org/projects/webkit/changeset/277452">r277452</a>. rdar://problem/78179698

    REGRESSION (<a href="http://trac.webkit.org/projects/webkit/changeset/276945">r276945</a>): [iOS] Focus rings are too large
    https://bugs.webkit.org/show_bug.cgi?id=225778
    <rdar://problem/77858341>

    Reviewed by Tim Horton.

    Source/WebCore:

    <a href="http://trac.webkit.org/projects/webkit/changeset/276945">r276945</a> updated scaling logic to ensure that the scale of the base CTM
    matches the device scale factor. The change itself makes our base CTM
    more correct, but exposed a longstanding bug with our focus ring
    implementation.

    Focus rings are drawn using CoreGraphics, using CGFocusRingStyle. On
    macOS, the style is initialized using NSInitializeCGFocusRingStyleForTime.
    However, on iOS, we initialize the style ourselves, using UIKit constants.
    Currently, the focus ring's style's radius is set to
    +[UIFocusRingStyle cornerRadius], a constant of 8. This is the longstanding
    issue. CGFocusRingStyle's radius is not a corner radius, but is the
    width of the focus ring. In UIKit, this width is represented by
    +[UIFocusRingStyle borderThickness], a constant of 3. WebKit has always
    intended to match this width, as evidenced by the default outline-width
    of 3px in the UA style sheet.

    Considering the large disparity between the existing and expected radius
    value, it may be surprising that this mistake has gone unnoticed since
    2019, when focus rings were first introduced on iOS. This is where <a href="http://trac.webkit.org/projects/webkit/changeset/276945">r276945</a>
    comes into play. Prior to <a href="http://trac.webkit.org/projects/webkit/changeset/276945">r276945</a>, the scale of the base CTM did not match
    the device scale factor. This meant that CG scaled down the constant of 8
    to 4 CSS pixels (1 (base CTM) / 2 (device scale factor)). After <a href="http://trac.webkit.org/projects/webkit/changeset/276945">r276945</a>,
    the two scales are equal and the focus ring is drawn as 8 CSS pixels, much
    larger than the expected 3px.

    Test: fast/forms/ios/focus-ring-size.html

    * platform/graphics/cocoa/GraphicsContextCocoa.mm:
    (WebCore::drawFocusRingAtTime):

    To fix, use the correct SPI to get the focus ring width,
    +[UIFocusRingStyle borderThickness]. This ensures that focus rings have
    the right width, following <a href="http://trac.webkit.org/projects/webkit/changeset/276945">r276945</a>.

    The change also fixes focus ring repaint issues that arose from the
    fact that the outline-width was 3px, but the painted width was 4px.

    Source/WebCore/PAL:

    * pal/spi/ios/UIKitSPI.h:

    LayoutTests:

    Added a regression test to verify the size of the focus ring on iOS.
    The test works by drawing an overlay on top of an input element, that
    is just large enough to obscure the focus ring. If the focus ring is
    too large, the ring will not obscured, leading to a mismatch failure.

    * fast/forms/ios/focus-ring-size-expected.html: Added.
    * fast/forms/ios/focus-ring-size.html: Added.

    git-svn-id: https://svn.webkit.org/repository/webkit/trunk@277452 268f45cc-cd09-0410-ab3c-d52691b4dbfc</pre>

<h3>Modified Paths</h3>
<ul>
<li><a href="#branchessafari6121154branchSourceWebCorePALpalspiiosUIKitSPIh">branches/safari-612.1.15.4-branch/Source/WebCore/PAL/pal/spi/ios/UIKitSPI.h</a></li>
<li><a href="#branchessafari6121154branchSourceWebCoreplatformgraphicscocoaGraphicsContextCocoamm">branches/safari-612.1.15.4-branch/Source/WebCore/platform/graphics/cocoa/GraphicsContextCocoa.mm</a></li>
</ul>

<h3>Added Paths</h3>
<ul>
<li><a href="#branchessafari6121154branchLayoutTestsfastformsiosfocusringsizeexpectedhtml">branches/safari-612.1.15.4-branch/LayoutTests/fast/forms/ios/focus-ring-size-expected.html</a></li>
<li><a href="#branchessafari6121154branchLayoutTestsfastformsiosfocusringsizehtml">branches/safari-612.1.15.4-branch/LayoutTests/fast/forms/ios/focus-ring-size.html</a></li>
</ul>

</div>
<div id="patch">
<h3>Diff</h3>
<a id="branchessafari6121154branchLayoutTestsfastformsiosfocusringsizeexpectedhtml"></a>
<div class="addfile"><h4>Added: branches/safari-612.1.15.4-branch/LayoutTests/fast/forms/ios/focus-ring-size-expected.html (0 => 278107)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-612.1.15.4-branch/LayoutTests/fast/forms/ios/focus-ring-size-expected.html                               (rev 0)
+++ branches/safari-612.1.15.4-branch/LayoutTests/fast/forms/ios/focus-ring-size-expected.html  2021-05-26 18:48:15 UTC (rev 278107)
</span><span class="lines">@@ -0,0 +1,28 @@
</span><ins>+<!DOCTYPE html>
+<html>
+<head>
+<style>
+
+:root {
+  --focus-ring-size: 3px;
+  --input-width: 160px;
+  --input-height: 20px;
+  --border-width: 1px;
+}
+
+#overlay {
+    position: absolute;
+    top: var(--focus-ring-size);
+    left: var(--focus-ring-size);
+    background-color: red;
+    border: var(--border-width) solid red;
+    width: calc(var(--input-width) + 2 * var(--focus-ring-size));
+    height: calc(var(--input-height) + 2 * var(--focus-ring-size));
+}
+
+</style>
+</head>
+<body>
+<div id="overlay"></div>
+</body>
+</html>
</ins></span></pre></div>
<a id="branchessafari6121154branchLayoutTestsfastformsiosfocusringsizehtml"></a>
<div class="addfile"><h4>Added: branches/safari-612.1.15.4-branch/LayoutTests/fast/forms/ios/focus-ring-size.html (0 => 278107)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-612.1.15.4-branch/LayoutTests/fast/forms/ios/focus-ring-size.html                                (rev 0)
+++ branches/safari-612.1.15.4-branch/LayoutTests/fast/forms/ios/focus-ring-size.html   2021-05-26 18:48:15 UTC (rev 278107)
</span><span class="lines">@@ -0,0 +1,50 @@
</span><ins>+<!DOCTYPE html>
+<html>
+<head>
+<script src="../../../resources/ui-helper.js"></script>
+<style>
+
+:root {
+  --focus-ring-size: 3px;
+  --input-width: 160px;
+  --input-height: 20px;
+  --border-width: 1px;
+}
+
+input {
+    caret-color: transparent;
+
+    position: absolute;
+    top: calc(2 * var(--focus-ring-size));
+    left: calc(2 * var(--focus-ring-size));
+    border: var(--border-width) solid black;
+    padding: 0;
+    width: var(--input-width);
+    height: var(--input-height);
+}
+
+#overlay {
+    position: absolute;
+    top: var(--focus-ring-size);
+    left: var(--focus-ring-size);
+    background-color: red;
+    border: var(--border-width) solid red;
+    width: calc(var(--input-width) + 2 * var(--focus-ring-size));
+    height: calc(var(--input-height) + 2 * var(--focus-ring-size));
+}
+
+</style>
+</head>
+<body>
+<input id="test" type="text">
+<div id="overlay"></div>
+<script>
+if (window.testRunner) {
+    testRunner.waitUntilDone();
+    let testElement = document.getElementById("test");
+    testElement.addEventListener("focus", () => testRunner.notifyDone(), { once: true });
+    UIHelper.keyDown("\t", ["altKey"]);
+}
+</script>
+</body>
+</html>
</ins></span></pre></div>
<a id="branchessafari6121154branchSourceWebCorePALpalspiiosUIKitSPIh"></a>
<div class="modfile"><h4>Modified: branches/safari-612.1.15.4-branch/Source/WebCore/PAL/pal/spi/ios/UIKitSPI.h (278106 => 278107)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-612.1.15.4-branch/Source/WebCore/PAL/pal/spi/ios/UIKitSPI.h      2021-05-26 18:48:12 UTC (rev 278106)
+++ branches/safari-612.1.15.4-branch/Source/WebCore/PAL/pal/spi/ios/UIKitSPI.h 2021-05-26 18:48:15 UTC (rev 278107)
</span><span class="lines">@@ -168,7 +168,7 @@
</span><span class="cx"> @end
</span><span class="cx"> 
</span><span class="cx"> @interface UIFocusRingStyle : NSObject
</span><del>-+ (CGFloat)cornerRadius;
</del><ins>++ (CGFloat)borderThickness;
</ins><span class="cx"> + (CGFloat)maxAlpha;
</span><span class="cx"> + (CGFloat)alphaThreshold;
</span><span class="cx"> @end
</span></span></pre></div>
<a id="branchessafari6121154branchSourceWebCoreplatformgraphicscocoaGraphicsContextCocoamm"></a>
<div class="modfile"><h4>Modified: branches/safari-612.1.15.4-branch/Source/WebCore/platform/graphics/cocoa/GraphicsContextCocoa.mm (278106 => 278107)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-612.1.15.4-branch/Source/WebCore/platform/graphics/cocoa/GraphicsContextCocoa.mm 2021-05-26 18:48:12 UTC (rev 278106)
+++ branches/safari-612.1.15.4-branch/Source/WebCore/platform/graphics/cocoa/GraphicsContextCocoa.mm    2021-05-26 18:48:15 UTC (rev 278107)
</span><span class="lines">@@ -74,7 +74,7 @@
</span><span class="cx">     focusRingStyle.tint = kCGFocusRingTintBlue;
</span><span class="cx">     focusRingStyle.ordering = kCGFocusRingOrderingNone;
</span><span class="cx">     focusRingStyle.alpha = [PAL::getUIFocusRingStyleClass() maxAlpha];
</span><del>-    focusRingStyle.radius = [PAL::getUIFocusRingStyleClass() cornerRadius];
</del><ins>+    focusRingStyle.radius = [PAL::getUIFocusRingStyleClass() borderThickness];
</ins><span class="cx">     focusRingStyle.threshold = [PAL::getUIFocusRingStyleClass() alphaThreshold];
</span><span class="cx">     focusRingStyle.bounds = CGRectZero;
</span><span class="cx"> #endif
</span></span></pre>
</div>
</div>

</body>
</html>