Title: [235769] trunk
Revision
235769
Author
wenson_hs...@apple.com
Date
2018-09-06 17:05:31 -0700 (Thu, 06 Sep 2018)

Log Message

[macOS] [WK2] Support changing attributes for selected text (text shadow, underline, strike-through)
https://bugs.webkit.org/show_bug.cgi?id=189356
<rdar://problem/44185674>

Reviewed by Tim Horton.

Source/WebCore:

Add support for encoding and decoding FontAttributeChanges, so that we can send FontAttributeChanges over IPC in
WebKit2. Also change m_verticalAlign to a new VerticalAlignChange enum type, so that it's no longer tied to the
CSS property values of "vertical-align", and can be encoded/decoded separately from VerticalAlign in
RenderStyleConstants.

Test: FontManagerTests.ChangeAttributesWithFontEffectsBox

* editing/FontAttributeChanges.cpp:
(WebCore::FontAttributeChanges::createEditingStyle const):
* editing/FontAttributeChanges.h:
(WebCore::FontAttributeChanges::setVerticalAlign):
(WebCore::FontShadow::encode const):
(WebCore::FontShadow::decode):
(WebCore::FontAttributeChanges::encode const):
(WebCore::FontAttributeChanges::decode):
* platform/mac/WebCoreNSFontManagerExtras.mm:
(WebCore::computedFontAttributeChanges):

Source/WebKit:

Implement -[WKWebView changeAttributes:], so that WKWebView can carry out more types of font style changes via
NSFontPanel. This patch makes it possible to (1) change text shadow, (2) add or remove strike-through, and (3)
add or remove underlines from selected text using the font panel.

This builds on the mechanisms introduced in r235748 to compute font attribute changes in the UI process and
propagate this information to the web process, where we're able to create and apply an EditingStyle to the
current selection.

* UIProcess/API/Cocoa/WKWebView.mm:
(-[WKWebView changeAttributes:]):
* UIProcess/Cocoa/WebViewImpl.h:
* UIProcess/Cocoa/WebViewImpl.mm:
(WebKit::WebViewImpl::changeFontAttributesFromSender):
* UIProcess/WebPageProxy.h:
* UIProcess/mac/WebPageProxyMac.mm:
(WebKit::WebPageProxy::changeFontAttributes):
* WebProcess/WebPage/WebPage.h:
* WebProcess/WebPage/WebPage.messages.in:

Add boilerplate IPC support.

* WebProcess/WebPage/mac/WebPageMac.mm:
(WebKit::WebPage::changeFontAttributes):

Tools:

Adds a new API test to verify that some font attributes (text shadow, underline, and strike-through) can be
added and removed using NSFontPanel.

* TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj:
* TestWebKitAPI/Tests/mac/FontManagerTests.mm:

Add the new API test.

(TestWebKitAPI::TEST):
* TestWebKitAPI/cocoa/TestWKWebView.h:
* TestWebKitAPI/mac/NSFontPanelTesting.h: Added.
* TestWebKitAPI/mac/NSFontPanelTesting.mm: Added.

Introduce a new file that extends NSFontPanel with some additional testing functionality. This includes the
ability to interact with the text shadow toggle button, choose the text shadow blur radius and opacity, and
change underline and strike-through styles.

(findSubviewOfClass):
(findMenuItemWithTitle):
(-[NSFontPanel fontEffectsBox]):

NSFontEffectsBox (an internal AppKit class) is the sender in the case where -changeAttributes: is invoked
through interaction with the font panel. To simulate this for testing, grab this font effects box and pass it
directory to -changeAttributes:.

(-[NSFontPanel chooseUnderlineMenuItemWithTitle:]):
(-[NSFontPanel chooseStrikeThroughMenuItemWithTitle:]):

The supported values for these menu items are "none" and "single", which adds a single underline or
strike-through to selected text. We grab these menu items by asking for the font panel's NSToolbar, and finding
the relevant menu items via toolbar item identifiers.

(-[NSFontPanel _didChangeAttributes]):
(-[NSFontPanel shadowBlurSlider]):
(-[NSFontPanel shadowOpacitySlider]):
(-[NSFontPanel shadowToggleButton]):
(-[NSFontPanel toggleShadow]):
(-[NSFontPanel shadowOpacity]):
(-[NSFontPanel setShadowOpacity:]):
(-[NSFontPanel shadowBlur]):
(-[NSFontPanel setShadowBlur:]):
(-[NSFontPanel _toolbarItemWithIdentifier:]):

Modified Paths

Added Paths

Diff

Modified: trunk/Source/WebCore/ChangeLog (235768 => 235769)


--- trunk/Source/WebCore/ChangeLog	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebCore/ChangeLog	2018-09-07 00:05:31 UTC (rev 235769)
@@ -1,3 +1,29 @@
+2018-09-06  Wenson Hsieh  <wenson_hs...@apple.com>
+
+        [macOS] [WK2] Support changing attributes for selected text (text shadow, underline, strike-through)
+        https://bugs.webkit.org/show_bug.cgi?id=189356
+        <rdar://problem/44185674>
+
+        Reviewed by Tim Horton.
+
+        Add support for encoding and decoding FontAttributeChanges, so that we can send FontAttributeChanges over IPC in
+        WebKit2. Also change m_verticalAlign to a new VerticalAlignChange enum type, so that it's no longer tied to the
+        CSS property values of "vertical-align", and can be encoded/decoded separately from VerticalAlign in
+        RenderStyleConstants.
+
+        Test: FontManagerTests.ChangeAttributesWithFontEffectsBox
+
+        * editing/FontAttributeChanges.cpp:
+        (WebCore::FontAttributeChanges::createEditingStyle const):
+        * editing/FontAttributeChanges.h:
+        (WebCore::FontAttributeChanges::setVerticalAlign):
+        (WebCore::FontShadow::encode const):
+        (WebCore::FontShadow::decode):
+        (WebCore::FontAttributeChanges::encode const):
+        (WebCore::FontAttributeChanges::decode):
+        * platform/mac/WebCoreNSFontManagerExtras.mm:
+        (WebCore::computedFontAttributeChanges):
+
 2018-09-06  Zalan Bujtas  <za...@apple.com>
 
         [LFC][BFC] Add support for min(max)-height

Modified: trunk/Source/WebCore/editing/FontAttributeChanges.cpp (235768 => 235769)


--- trunk/Source/WebCore/editing/FontAttributeChanges.cpp	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebCore/editing/FontAttributeChanges.cpp	2018-09-07 00:05:31 UTC (rev 235769)
@@ -112,14 +112,19 @@
     }
 
     if (m_verticalAlign) {
-        if (*m_verticalAlign == VerticalAlign::Super)
+        switch (*m_verticalAlign) {
+        case VerticalAlignChange::Superscript:
             style->setProperty(CSSPropertyVerticalAlign, CSSValueSuper);
-        else if (*m_verticalAlign == VerticalAlign::Sub)
+            break;
+        case VerticalAlignChange::Subscript:
             style->setProperty(CSSPropertyVerticalAlign, CSSValueSub);
-        else if (*m_verticalAlign == VerticalAlign::Baseline)
+            break;
+        case VerticalAlignChange::Baseline:
             style->setProperty(CSSPropertyVerticalAlign, CSSValueBaseline);
-        else
+            break;
+        default:
             ASSERT_NOT_REACHED();
+        }
     }
 
     auto editingStyle = EditingStyle::create(style.ptr());

Modified: trunk/Source/WebCore/editing/FontAttributeChanges.h (235768 => 235769)


--- trunk/Source/WebCore/editing/FontAttributeChanges.h	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebCore/editing/FontAttributeChanges.h	2018-09-07 00:05:31 UTC (rev 235769)
@@ -26,7 +26,7 @@
 #pragma once
 
 #include "Color.h"
-#include "RenderStyleConstants.h"
+#include <wtf/EnumTraits.h>
 #include <wtf/Forward.h>
 #include <wtf/Optional.h>
 
@@ -35,6 +35,8 @@
 class EditingStyle;
 class MutableStyleProperties;
 
+enum class VerticalAlignChange : uint8_t { Superscript, Baseline, Subscript };
+
 class FontChanges {
 public:
     template<class Encoder> void encode(Encoder&) const;
@@ -62,6 +64,9 @@
 };
 
 struct FontShadow {
+    template<class Encoder> void encode(Encoder&) const;
+    template<class Decoder> static bool decode(Decoder&, FontShadow&);
+
     Color color;
     double width { 0 };
     double height { 0 };
@@ -70,7 +75,10 @@
 
 class FontAttributeChanges {
 public:
-    void setVerticalAlign(VerticalAlign align) { m_verticalAlign = align; }
+    template<class Encoder> void encode(Encoder&) const;
+    template<class Decoder> static bool decode(Decoder&, FontAttributeChanges&);
+
+    void setVerticalAlign(VerticalAlignChange align) { m_verticalAlign = align; }
     void setBackgroundColor(const Color& color) { m_backgroundColor = color; }
     void setForegroundColor(const Color& color) { m_foregroundColor = color; }
     void setShadow(const FontShadow& shadow) { m_shadow = shadow; }
@@ -81,7 +89,7 @@
     WEBCORE_EXPORT Ref<EditingStyle> createEditingStyle() const;
 
 private:
-    std::optional<VerticalAlign> m_verticalAlign;
+    std::optional<VerticalAlignChange> m_verticalAlign;
     std::optional<Color> m_backgroundColor;
     std::optional<Color> m_foregroundColor;
     std::optional<FontShadow> m_shadow;
@@ -122,4 +130,72 @@
     return true;
 }
 
+template<class Encoder>
+void FontShadow::encode(Encoder& encoder) const
+{
+    encoder << color << width << height << blurRadius;
+}
+
+template<class Decoder>
+bool FontShadow::decode(Decoder& decoder, FontShadow& shadow)
+{
+    if (!decoder.decode(shadow.color))
+        return false;
+
+    if (!decoder.decode(shadow.width))
+        return false;
+
+    if (!decoder.decode(shadow.height))
+        return false;
+
+    if (!decoder.decode(shadow.blurRadius))
+        return false;
+
+    return true;
+}
+
+template<class Encoder>
+void FontAttributeChanges::encode(Encoder& encoder) const
+{
+    encoder << m_verticalAlign << m_backgroundColor << m_foregroundColor << m_shadow << m_strikeThrough << m_underline << m_fontChanges;
+}
+
+template<class Decoder>
+bool FontAttributeChanges::decode(Decoder& decoder, FontAttributeChanges& changes)
+{
+    if (!decoder.decode(changes.m_verticalAlign))
+        return false;
+
+    if (!decoder.decode(changes.m_backgroundColor))
+        return false;
+
+    if (!decoder.decode(changes.m_foregroundColor))
+        return false;
+
+    if (!decoder.decode(changes.m_shadow))
+        return false;
+
+    if (!decoder.decode(changes.m_strikeThrough))
+        return false;
+
+    if (!decoder.decode(changes.m_underline))
+        return false;
+
+    if (!decoder.decode(changes.m_fontChanges))
+        return false;
+
+    return true;
+}
+
 } // namespace WebCore
+
+namespace WTF {
+template<> struct EnumTraits<WebCore::VerticalAlignChange> {
+    using values = EnumValues<
+        WebCore::VerticalAlignChange,
+        WebCore::VerticalAlignChange::Superscript,
+        WebCore::VerticalAlignChange::Baseline,
+        WebCore::VerticalAlignChange::Subscript
+    >;
+};
+}

Modified: trunk/Source/WebCore/platform/mac/WebCoreNSFontManagerExtras.mm (235768 => 235769)


--- trunk/Source/WebCore/platform/mac/WebCoreNSFontManagerExtras.mm	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebCore/platform/mac/WebCoreNSFontManagerExtras.mm	2018-09-07 00:05:31 UTC (rev 235769)
@@ -144,11 +144,11 @@
     int convertedSuperscriptA = [[convertedAttributesA objectForKey:NSSuperscriptAttributeName] intValue];
     if (convertedSuperscriptA == [[convertedAttributesB objectForKey:NSSuperscriptAttributeName] intValue]) {
         if (convertedSuperscriptA > 0)
-            changes.setVerticalAlign(VerticalAlign::Super);
+            changes.setVerticalAlign(VerticalAlignChange::Superscript);
         else if (convertedSuperscriptA < 0)
-            changes.setVerticalAlign(VerticalAlign::Sub);
+            changes.setVerticalAlign(VerticalAlignChange::Subscript);
         else
-            changes.setVerticalAlign(VerticalAlign::Baseline);
+            changes.setVerticalAlign(VerticalAlignChange::Baseline);
     }
 
     int convertedStrikeThroughA = [[convertedAttributesA objectForKey:NSStrikethroughStyleAttributeName] intValue];

Modified: trunk/Source/WebKit/ChangeLog (235768 => 235769)


--- trunk/Source/WebKit/ChangeLog	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebKit/ChangeLog	2018-09-07 00:05:31 UTC (rev 235769)
@@ -1,3 +1,35 @@
+2018-09-06  Wenson Hsieh  <wenson_hs...@apple.com>
+
+        [macOS] [WK2] Support changing attributes for selected text (text shadow, underline, strike-through)
+        https://bugs.webkit.org/show_bug.cgi?id=189356
+        <rdar://problem/44185674>
+
+        Reviewed by Tim Horton.
+
+        Implement -[WKWebView changeAttributes:], so that WKWebView can carry out more types of font style changes via
+        NSFontPanel. This patch makes it possible to (1) change text shadow, (2) add or remove strike-through, and (3)
+        add or remove underlines from selected text using the font panel.
+
+        This builds on the mechanisms introduced in r235748 to compute font attribute changes in the UI process and
+        propagate this information to the web process, where we're able to create and apply an EditingStyle to the
+        current selection.
+
+        * UIProcess/API/Cocoa/WKWebView.mm:
+        (-[WKWebView changeAttributes:]):
+        * UIProcess/Cocoa/WebViewImpl.h:
+        * UIProcess/Cocoa/WebViewImpl.mm:
+        (WebKit::WebViewImpl::changeFontAttributesFromSender):
+        * UIProcess/WebPageProxy.h:
+        * UIProcess/mac/WebPageProxyMac.mm:
+        (WebKit::WebPageProxy::changeFontAttributes):
+        * WebProcess/WebPage/WebPage.h:
+        * WebProcess/WebPage/WebPage.messages.in:
+
+        Add boilerplate IPC support.
+
+        * WebProcess/WebPage/mac/WebPageMac.mm:
+        (WebKit::WebPage::changeFontAttributes):
+
 2018-09-06  Antti Koivisto  <an...@apple.com>
 
         Actively prewarm processes created for prewarm pool

Modified: trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebView.mm (235768 => 235769)


--- trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebView.mm	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebView.mm	2018-09-07 00:05:31 UTC (rev 235769)
@@ -3359,6 +3359,11 @@
     _impl->changeFontFromFontManager();
 }
 
+- (void)changeAttributes:(id)sender
+{
+    _impl->changeFontAttributesFromSender(sender);
+}
+
 - (IBAction)startSpeaking:(id)sender
 {
     _impl->startSpeaking();

Modified: trunk/Source/WebKit/UIProcess/Cocoa/WebViewImpl.h (235768 => 235769)


--- trunk/Source/WebKit/UIProcess/Cocoa/WebViewImpl.h	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebKit/UIProcess/Cocoa/WebViewImpl.h	2018-09-07 00:05:31 UTC (rev 235769)
@@ -316,6 +316,7 @@
     void didBecomeEditable();
     void updateFontPanelIfNeeded();
     void changeFontFromFontManager();
+    void changeFontAttributesFromSender(id);
     bool validateUserInterfaceItem(id <NSValidatedUserInterfaceItem>);
     void setEditableElementIsFocused(bool);
 

Modified: trunk/Source/WebKit/UIProcess/Cocoa/WebViewImpl.mm (235768 => 235769)


--- trunk/Source/WebKit/UIProcess/Cocoa/WebViewImpl.mm	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebKit/UIProcess/Cocoa/WebViewImpl.mm	2018-09-07 00:05:31 UTC (rev 235769)
@@ -2734,6 +2734,16 @@
     }
 }
 
+void WebViewImpl::changeFontAttributesFromSender(id sender)
+{
+    auto& editorState = m_page->editorState();
+    if (!editorState.isContentEditable || editorState.selectionIsNone)
+        return;
+
+    m_page->changeFontAttributes(WebCore::computedFontAttributeChanges(NSFontManager.sharedFontManager, sender));
+    updateFontPanelIfNeeded();
+}
+
 void WebViewImpl::changeFontFromFontManager()
 {
     auto& editorState = m_page->editorState();

Modified: trunk/Source/WebKit/UIProcess/WebPageProxy.h (235768 => 235769)


--- trunk/Source/WebKit/UIProcess/WebPageProxy.h	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebKit/UIProcess/WebPageProxy.h	2018-09-07 00:05:31 UTC (rev 235769)
@@ -162,6 +162,7 @@
 class Cursor;
 class DragData;
 class FloatRect;
+class FontAttributeChanges;
 class FontChanges;
 class GraphicsLayer;
 class IntSize;
@@ -681,6 +682,7 @@
 #if PLATFORM(MAC)
     void insertDictatedTextAsync(const String& text, const EditingRange& replacementRange, const Vector<WebCore::TextAlternativeWithRange>& dictationAlternatives, bool registerUndoGroup);
     void attributedSubstringForCharacterRangeAsync(const EditingRange&, WTF::Function<void (const AttributedString&, const EditingRange&, CallbackBase::Error)>&&);
+    void changeFontAttributes(WebCore::FontAttributeChanges&&);
     void changeFont(WebCore::FontChanges&&);
     void fontAtSelection(WTF::Function<void (const String&, double, bool, CallbackBase::Error)>&&);
 

Modified: trunk/Source/WebKit/UIProcess/mac/WebPageProxyMac.mm (235768 => 235769)


--- trunk/Source/WebKit/UIProcess/mac/WebPageProxyMac.mm	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebKit/UIProcess/mac/WebPageProxyMac.mm	2018-09-07 00:05:31 UTC (rev 235769)
@@ -626,6 +626,14 @@
 {
     return MacApplication::isAppleMail();
 }
+
+void WebPageProxy::changeFontAttributes(WebCore::FontAttributeChanges&& changes)
+{
+    if (!isValid())
+        return;
+
+    process().send(Messages::WebPage::ChangeFontAttributes(WTFMove(changes)), m_pageID);
+}
     
 void WebPageProxy::changeFont(WebCore::FontChanges&& changes)
 {

Modified: trunk/Source/WebKit/WebProcess/WebPage/WebPage.h (235768 => 235769)


--- trunk/Source/WebKit/WebProcess/WebPage/WebPage.h	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebKit/WebProcess/WebPage/WebPage.h	2018-09-07 00:05:31 UTC (rev 235769)
@@ -135,6 +135,7 @@
 class CaptureDevice;
 class DocumentLoader;
 class DragData;
+class FontAttributeChanges;
 class FontChanges;
 class Frame;
 class FrameSelection;
@@ -1363,6 +1364,7 @@
     void immediateActionDidCancel();
     void immediateActionDidComplete();
     void changeFont(WebCore::FontChanges&&);
+    void changeFontAttributes(WebCore::FontAttributeChanges&&);
 
     void dataDetectorsDidPresentUI(WebCore::PageOverlay::PageOverlayID);
     void dataDetectorsDidChangeUI(WebCore::PageOverlay::PageOverlayID);

Modified: trunk/Source/WebKit/WebProcess/WebPage/WebPage.messages.in (235768 => 235769)


--- trunk/Source/WebKit/WebProcess/WebPage/WebPage.messages.in	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebKit/WebProcess/WebPage/WebPage.messages.in	2018-09-07 00:05:31 UTC (rev 235769)
@@ -191,6 +191,7 @@
 #if PLATFORM(MAC)
     PerformDictionaryLookupOfCurrentSelection()
     ChangeFont(WebCore::FontChanges changes)
+    ChangeFontAttributes(WebCore::FontAttributeChanges changes)
 #endif
 
     PreferencesDidChange(struct WebKit::WebPreferencesStore store)

Modified: trunk/Source/WebKit/WebProcess/WebPage/mac/WebPageMac.mm (235768 => 235769)


--- trunk/Source/WebKit/WebProcess/WebPage/mac/WebPageMac.mm	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Source/WebKit/WebProcess/WebPage/mac/WebPageMac.mm	2018-09-07 00:05:31 UTC (rev 235769)
@@ -1115,6 +1115,13 @@
     }
 }
 
+void WebPage::changeFontAttributes(WebCore::FontAttributeChanges&& changes)
+{
+    auto& frame = m_page->focusController().focusedOrMainFrame();
+    if (frame.selection().selection().isContentEditable())
+        frame.editor().applyStyleToSelection(changes.createEditingStyle(), EditActionChangeAttributes, Editor::ColorFilterMode::InvertColor);
+}
+
 void WebPage::changeFont(WebCore::FontChanges&& changes)
 {
     auto& frame = m_page->focusController().focusedOrMainFrame();

Modified: trunk/Tools/ChangeLog (235768 => 235769)


--- trunk/Tools/ChangeLog	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Tools/ChangeLog	2018-09-07 00:05:31 UTC (rev 235769)
@@ -1,3 +1,54 @@
+2018-09-06  Wenson Hsieh  <wenson_hs...@apple.com>
+
+        [macOS] [WK2] Support changing attributes for selected text (text shadow, underline, strike-through)
+        https://bugs.webkit.org/show_bug.cgi?id=189356
+        <rdar://problem/44185674>
+
+        Reviewed by Tim Horton.
+
+        Adds a new API test to verify that some font attributes (text shadow, underline, and strike-through) can be
+        added and removed using NSFontPanel.
+
+        * TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj:
+        * TestWebKitAPI/Tests/mac/FontManagerTests.mm:
+
+        Add the new API test.
+
+        (TestWebKitAPI::TEST):
+        * TestWebKitAPI/cocoa/TestWKWebView.h:
+        * TestWebKitAPI/mac/NSFontPanelTesting.h: Added.
+        * TestWebKitAPI/mac/NSFontPanelTesting.mm: Added.
+
+        Introduce a new file that extends NSFontPanel with some additional testing functionality. This includes the
+        ability to interact with the text shadow toggle button, choose the text shadow blur radius and opacity, and
+        change underline and strike-through styles.
+
+        (findSubviewOfClass):
+        (findMenuItemWithTitle):
+        (-[NSFontPanel fontEffectsBox]):
+
+        NSFontEffectsBox (an internal AppKit class) is the sender in the case where -changeAttributes: is invoked
+        through interaction with the font panel. To simulate this for testing, grab this font effects box and pass it
+        directory to -changeAttributes:.
+
+        (-[NSFontPanel chooseUnderlineMenuItemWithTitle:]):
+        (-[NSFontPanel chooseStrikeThroughMenuItemWithTitle:]):
+
+        The supported values for these menu items are "none" and "single", which adds a single underline or
+        strike-through to selected text. We grab these menu items by asking for the font panel's NSToolbar, and finding
+        the relevant menu items via toolbar item identifiers.
+
+        (-[NSFontPanel _didChangeAttributes]):
+        (-[NSFontPanel shadowBlurSlider]):
+        (-[NSFontPanel shadowOpacitySlider]):
+        (-[NSFontPanel shadowToggleButton]):
+        (-[NSFontPanel toggleShadow]):
+        (-[NSFontPanel shadowOpacity]):
+        (-[NSFontPanel setShadowOpacity:]):
+        (-[NSFontPanel shadowBlur]):
+        (-[NSFontPanel setShadowBlur:]):
+        (-[NSFontPanel _toolbarItemWithIdentifier:]):
+
 2018-09-06  Simon Fraser  <simon.fra...@apple.com>
 
         run-webkit-tests prints confusing messages when test expectations list results that are not compatible with the run options

Modified: trunk/Tools/TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj (235768 => 235769)


--- trunk/Tools/TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Tools/TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj	2018-09-07 00:05:31 UTC (rev 235769)
@@ -794,6 +794,7 @@
 		F42DA5161D8CEFE400336F40 /* large-input-field-focus-onload.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = F42DA5151D8CEFDB00336F40 /* large-input-field-focus-onload.html */; };
 		F43E3BBF20DADA1E00A4E7ED /* WKScrollViewTests.mm in Sources */ = {isa = PBXBuildFile; fileRef = F43E3BBE20DADA1E00A4E7ED /* WKScrollViewTests.mm */; };
 		F43E3BC120DADBC500A4E7ED /* fixed-nav-bar.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = F43E3BC020DADB8000A4E7ED /* fixed-nav-bar.html */; };
+		F442851D2140DF2900CCDA22 /* NSFontPanelTesting.mm in Sources */ = {isa = PBXBuildFile; fileRef = F442851C2140DF2900CCDA22 /* NSFontPanelTesting.mm */; };
 		F4451C761EB8FD890020C5DA /* two-paragraph-contenteditable.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = F4451C751EB8FD7C0020C5DA /* two-paragraph-contenteditable.html */; };
 		F44C79FF20F9E8710014478C /* ParserYieldTokenTests.mm in Sources */ = {isa = PBXBuildFile; fileRef = F44C79FE20F9E8710014478C /* ParserYieldTokenTests.mm */; };
 		F44C7A0020F9EEBF0014478C /* ParserYieldTokenPlugIn.mm in Sources */ = {isa = PBXBuildFile; fileRef = F44C79FB20F9E50C0014478C /* ParserYieldTokenPlugIn.mm */; };
@@ -2035,6 +2036,8 @@
 		F42DA5151D8CEFDB00336F40 /* large-input-field-focus-onload.html */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.html; name = "large-input-field-focus-onload.html"; path = "Tests/WebKitCocoa/large-input-field-focus-onload.html"; sourceTree = SOURCE_ROOT; };
 		F43E3BBE20DADA1E00A4E7ED /* WKScrollViewTests.mm */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.objcpp; path = WKScrollViewTests.mm; sourceTree = "<group>"; };
 		F43E3BC020DADB8000A4E7ED /* fixed-nav-bar.html */ = {isa = PBXFileReference; lastKnownFileType = text.html; path = "fixed-nav-bar.html"; sourceTree = "<group>"; };
+		F442851B2140DF2900CCDA22 /* NSFontPanelTesting.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = NSFontPanelTesting.h; sourceTree = "<group>"; };
+		F442851C2140DF2900CCDA22 /* NSFontPanelTesting.mm */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.objcpp; path = NSFontPanelTesting.mm; sourceTree = "<group>"; };
 		F4451C751EB8FD7C0020C5DA /* two-paragraph-contenteditable.html */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.html; path = "two-paragraph-contenteditable.html"; sourceTree = "<group>"; };
 		F44C79FB20F9E50C0014478C /* ParserYieldTokenPlugIn.mm */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.objcpp; path = ParserYieldTokenPlugIn.mm; sourceTree = "<group>"; };
 		F44C79FD20F9E8710014478C /* ParserYieldTokenTests.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = ParserYieldTokenTests.h; sourceTree = "<group>"; };
@@ -3149,6 +3152,8 @@
 				1AEDE22413E5E7A000E62FE8 /* InjectedBundleControllerMac.mm */,
 				C081224013FC172400DC39AE /* _javascript_TestMac.mm */,
 				2E7765CE16C4D81100BA2BB1 /* mainMac.mm */,
+				F442851B2140DF2900CCDA22 /* NSFontPanelTesting.h */,
+				F442851C2140DF2900CCDA22 /* NSFontPanelTesting.mm */,
 				BC131884117114B600B69727 /* PlatformUtilitiesMac.mm */,
 				BC90955C125548AA00083756 /* PlatformWebViewMac.mm */,
 				C081224313FC19EC00DC39AE /* SyntheticBackingScaleFactorWindow.h */,
@@ -3880,6 +3885,7 @@
 				CD2D0D1A213465560018C784 /* NowPlaying.mm in Sources */,
 				2ECFF5551D9B12F800B55394 /* NowPlayingControlsTests.mm in Sources */,
 				A10F047E1E3AD29C00C95E19 /* NSFileManagerExtras.mm in Sources */,
+				F442851D2140DF2900CCDA22 /* NSFontPanelTesting.mm in Sources */,
 				37A22AA71DCAA27200AFBFC4 /* ObservedRenderingProgressEventsAfterCrash.mm in Sources */,
 				7CCE7F251A411AF600447C4C /* OpenAndCloseWindow.mm in Sources */,
 				CEBCA12F1E3A660100C73293 /* OverrideContentSecurityPolicy.mm in Sources */,

Modified: trunk/Tools/TestWebKitAPI/Tests/mac/FontManagerTests.mm (235768 => 235769)


--- trunk/Tools/TestWebKitAPI/Tests/mac/FontManagerTests.mm	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Tools/TestWebKitAPI/Tests/mac/FontManagerTests.mm	2018-09-07 00:05:31 UTC (rev 235769)
@@ -27,6 +27,8 @@
 
 #if PLATFORM(MAC) && WK_API_ENABLED
 
+#import "AppKitSPI.h"
+#import "NSFontPanelTesting.h"
 #import "PlatformUtilities.h"
 #import "TestWKWebView.h"
 #import <WebKit/WKWebViewPrivate.h>
@@ -178,6 +180,74 @@
     EXPECT_EQ(largeItalicLightAvenirFont, fontManager.selectedFont);
 }
 
+TEST(FontManagerTests, ChangeAttributesWithFontEffectsBox)
+{
+    NSFontManager *fontManager = [NSFontManager sharedFontManager];
+    auto webView = webViewForFontManagerTesting(fontManager);
+
+    NSFontPanel *fontPanel = [fontManager fontPanel:YES];
+    [fontPanel setIsVisible:YES];
+
+    auto textDecorationsAroundSelection = [webView] {
+        NSString *decorationsAtStart = [webView stylePropertyAtSelectionStart:@"-webkit-text-decorations-in-effect"];
+        NSString *decorationsAtEnd = [webView stylePropertyAtSelectionEnd:@"-webkit-text-decorations-in-effect"];
+        if ([decorationsAtStart isEqualToString:decorationsAtEnd] || decorationsAtStart == decorationsAtEnd)
+            return decorationsAtStart;
+        return [NSString stringWithFormat:@"(%@, %@)", decorationsAtStart, decorationsAtEnd];
+    };
+
+    auto textShadowAroundSelection = [webView] {
+        NSString *shadowAtStart = [webView stylePropertyAtSelectionStart:@"text-shadow"];
+        NSString *shadowAtEnd = [webView stylePropertyAtSelectionEnd:@"text-shadow"];
+        if ([shadowAtStart isEqualToString:shadowAtEnd] || shadowAtStart == shadowAtEnd)
+            return shadowAtStart;
+        return [NSString stringWithFormat:@"(%@, %@)", shadowAtStart, shadowAtEnd];
+    };
+
+    [webView selectWord:nil];
+    [fontPanel chooseUnderlineMenuItemWithTitle:@"single"];
+    EXPECT_WK_STREQ("foo", [webView selectedText]);
+    EXPECT_WK_STREQ("underline", textDecorationsAroundSelection());
+
+    [fontPanel chooseUnderlineMenuItemWithTitle:@"none"];
+    EXPECT_WK_STREQ("none", textDecorationsAroundSelection());
+
+    [webView selectNextWord];
+    [fontPanel chooseStrikeThroughMenuItemWithTitle:@"single"];
+    EXPECT_WK_STREQ("bar", [webView selectedText]);
+    EXPECT_WK_STREQ("line-through", textDecorationsAroundSelection());
+
+    [fontPanel chooseStrikeThroughMenuItemWithTitle:@"none"];
+    EXPECT_WK_STREQ("none", textDecorationsAroundSelection());
+
+    [webView selectNextWord];
+    fontPanel.shadowBlur = 8;
+    fontPanel.shadowOpacity = 1;
+    [fontPanel toggleShadow];
+    EXPECT_WK_STREQ("baz", [webView selectedText]);
+    EXPECT_WK_STREQ("rgb(0, 0, 0) 0px 1px 8px", textShadowAroundSelection());
+
+    [fontPanel toggleShadow];
+    EXPECT_WK_STREQ("none", textShadowAroundSelection());
+
+    // Now combine all three attributes together.
+    [webView selectAll:nil];
+    fontPanel.shadowBlur = 5;
+    fontPanel.shadowOpacity = 0.2;
+    [fontPanel toggleShadow];
+    [fontPanel chooseUnderlineMenuItemWithTitle:@"single"];
+    [fontPanel chooseStrikeThroughMenuItemWithTitle:@"single"];
+    EXPECT_WK_STREQ("foo bar baz", [webView selectedText]);
+    EXPECT_WK_STREQ("rgba(0, 0, 0, 0.2) 0px 1px 5px", textShadowAroundSelection());
+    EXPECT_WK_STREQ("underline line-through", textDecorationsAroundSelection());
+
+    [fontPanel toggleShadow];
+    [fontPanel chooseUnderlineMenuItemWithTitle:@"none"];
+    [fontPanel chooseStrikeThroughMenuItemWithTitle:@"none"];
+    EXPECT_WK_STREQ("none", textShadowAroundSelection());
+    EXPECT_WK_STREQ("none", textDecorationsAroundSelection());
+}
+
 } // namespace TestWebKitAPI
 
 #endif // PLATFORM(MAC) && WK_API_ENABLED

Modified: trunk/Tools/TestWebKitAPI/cocoa/TestWKWebView.h (235768 => 235769)


--- trunk/Tools/TestWebKitAPI/cocoa/TestWKWebView.h	2018-09-06 23:52:05 UTC (rev 235768)
+++ trunk/Tools/TestWebKitAPI/cocoa/TestWKWebView.h	2018-09-07 00:05:31 UTC (rev 235769)
@@ -37,6 +37,7 @@
 @interface WKWebView (AdditionalDeclarations)
 #if PLATFORM(MAC)
 - (void)paste:(id)sender;
+- (void)changeAttributes:(id)sender;
 #endif
 @end
 

Added: trunk/Tools/TestWebKitAPI/mac/NSFontPanelTesting.h (0 => 235769)


--- trunk/Tools/TestWebKitAPI/mac/NSFontPanelTesting.h	                        (rev 0)
+++ trunk/Tools/TestWebKitAPI/mac/NSFontPanelTesting.h	2018-09-07 00:05:31 UTC (rev 235769)
@@ -0,0 +1,43 @@
+/*
+ * Copyright (C) 2018 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#pragma once
+
+#if PLATFORM(MAC) && WK_API_ENABLED
+
+#import <AppKit/AppKit.h>
+
+@interface NSFontPanel (TestWebKitAPI)
+
+@property (nonatomic) double shadowOpacity;
+@property (nonatomic) double shadowBlur;
+
+- (void)toggleShadow;
+- (void)chooseUnderlineMenuItemWithTitle:(NSString *)itemTitle;
+- (void)chooseStrikeThroughMenuItemWithTitle:(NSString *)itemTitle;
+
+@end
+
+#endif

Added: trunk/Tools/TestWebKitAPI/mac/NSFontPanelTesting.mm (0 => 235769)


--- trunk/Tools/TestWebKitAPI/mac/NSFontPanelTesting.mm	                        (rev 0)
+++ trunk/Tools/TestWebKitAPI/mac/NSFontPanelTesting.mm	2018-09-07 00:05:31 UTC (rev 235769)
@@ -0,0 +1,153 @@
+/*
+ * Copyright (C) 2018 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "config.h"
+#include "NSFontPanelTesting.h"
+
+#if PLATFORM(MAC) && WK_API_ENABLED
+
+#import <objc/runtime.h>
+
+#if __MAC_OS_X_VERSION_MAX_ALLOWED < 101300
+static const NSCellStateValue NSControlStateValueOff = NSOffState;
+static const NSCellStateValue NSControlStateValueOn = NSOnState;
+#endif
+
+@interface NSBox (NSFontEffectsBox)
+// Invoked after a font effect (e.g. single strike-through) is chosen.
+- (void)_openEffectsButton:(id)sender;
+@end
+
+static NSView *findSubviewOfClass(NSView *view, Class targetClass)
+{
+    if ([view isKindOfClass:targetClass])
+        return view;
+
+    for (NSView *subview in view.subviews) {
+        if (NSView *targetView = findSubviewOfClass(subview, targetClass))
+            return targetView;
+    }
+    return nil;
+}
+
+static NSMenuItem *findMenuItemWithTitle(NSPopUpButton *button, NSString *title)
+{
+    for (NSMenuItem *item in button.itemArray) {
+        if ([item.title.lowercaseString isEqualToString:title.lowercaseString])
+            return item;
+    }
+    return nil;
+}
+
+@implementation NSFontPanel (TestWebKitAPI)
+
+- (NSBox *)fontEffectsBox
+{
+    void* result = nullptr;
+    object_getInstanceVariable(self, "_fontEffectsBox", &result);
+    return static_cast<NSBox *>(result);
+}
+
+- (void)chooseUnderlineMenuItemWithTitle:(NSString *)itemTitle
+{
+    NSPopUpButton *button = (NSPopUpButton *)[self _toolbarItemWithIdentifier:@"NSFontPanelUnderlineToolbarItem"].view;
+    [button selectItem:findMenuItemWithTitle(button, itemTitle)];
+    [self.fontEffectsBox _openEffectsButton:button];
+    [self _didChangeAttributes];
+}
+
+- (void)chooseStrikeThroughMenuItemWithTitle:(NSString *)itemTitle
+{
+    NSPopUpButton *button = (NSPopUpButton *)[self _toolbarItemWithIdentifier:@"NSFontPanelStrikethroughToolbarItem"].view;
+    [button selectItem:findMenuItemWithTitle(button, itemTitle)];
+    [self.fontEffectsBox _openEffectsButton:button];
+    [self _didChangeAttributes];
+}
+
+- (void)_didChangeAttributes
+{
+    NSFontManager *fontManager = NSFontManager.sharedFontManager;
+    if (self == [fontManager fontPanel:NO])
+        [fontManager.target changeAttributes:self.fontEffectsBox];
+}
+
+- (NSSlider *)shadowBlurSlider
+{
+    return (NSSlider *)findSubviewOfClass([self _toolbarItemWithIdentifier:@"NSFontPanelShadowBlurToolbarItem"].view, NSSlider.class);
+}
+
+- (NSSlider *)shadowOpacitySlider
+{
+    return (NSSlider *)findSubviewOfClass([self _toolbarItemWithIdentifier:@"NSFontPanelShadowOpacityToolbarItem"].view, NSSlider.class);
+}
+
+- (NSButton *)shadowToggleButton
+{
+    return (NSButton *)[self _toolbarItemWithIdentifier:@"NSFontPanelShadowToggleToolbarItem"].view;
+}
+
+- (void)toggleShadow
+{
+    NSButton *shadowToggleButton = self.shadowToggleButton;
+    shadowToggleButton.state = shadowToggleButton.state == NSControlStateValueOff ? NSControlStateValueOn : NSControlStateValueOff;
+    [self _didChangeAttributes];
+}
+
+- (double)shadowOpacity
+{
+    return self.shadowOpacitySlider.doubleValue;
+}
+
+- (void)setShadowOpacity:(double)shadowOpacity
+{
+    self.shadowOpacitySlider.doubleValue = shadowOpacity;
+    if (self.shadowToggleButton.state == NSControlStateValueOn)
+        [self _didChangeAttributes];
+}
+
+- (double)shadowBlur
+{
+    return self.shadowBlurSlider.doubleValue;
+}
+
+- (void)setShadowBlur:(double)shadowBlur
+{
+    self.shadowBlurSlider.doubleValue = shadowBlur;
+    if (self.shadowToggleButton.state == NSControlStateValueOn)
+        [self _didChangeAttributes];
+}
+
+- (NSToolbarItem *)_toolbarItemWithIdentifier:(NSString *)itemIdentifier
+{
+    for (NSToolbarItem *item in self.toolbar.items) {
+        if ([item.itemIdentifier isEqualToString:itemIdentifier])
+            return item;
+    }
+    return nil;
+}
+
+@end
+
+#endif // PLATFORM(MAC) && WK_API_ENABLED
_______________________________________________
webkit-changes mailing list
webkit-changes@lists.webkit.org
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to