Occasional assertion failure under recommendedScrollbarStyleDidChange()
authortimothy_horton@apple.com <timothy_horton@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Tue, 11 Nov 2014 21:39:46 +0000 (21:39 +0000)
committertimothy_horton@apple.com <timothy_horton@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Tue, 11 Nov 2014 21:39:46 +0000 (21:39 +0000)
https://bugs.webkit.org/show_bug.cgi?id=138604
<rdar://problem/18855914>

Reviewed by Beth Dakin.

It is possible for AppKit to install tracking areas into our view
behind our back, but we have code that depends on knowing exactly
the set of tracking areas installed on WKView.

Make this more robust by keeping a reference to the tracking area we
use for many things and manipulating that instead of making assumptions
about the total set of tracking areas on WKView.

* UIProcess/API/mac/WKView.mm:
(-[WKView _primaryTrackingArea]):
(-[WKView _replacePrimaryTrackingArea:]):
Provide a 'primary' tracking area setter/getter.

(-[WKView initWithFrame:context:configuration:webView:]):
Keep a reference to the original tracking area installed at initialization time.

* UIProcess/API/mac/WKViewInternal.h:
* UIProcess/mac/PageClientImpl.mm:
(WebKit::PageClientImpl::recommendedScrollbarStyleDidChange):
Instead of walking the set of tracking areas, make use of the fact that
we know exactly which tracking area we installed, and uninstall just that
one, and replace it with our newly-built one.

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@175973 268f45cc-cd09-0410-ab3c-d52691b4dbfc

Source/WebKit2/ChangeLog
Source/WebKit2/UIProcess/API/mac/WKView.mm
Source/WebKit2/UIProcess/API/mac/WKViewInternal.h
Source/WebKit2/UIProcess/mac/PageClientImpl.mm

index 55cbea4..d19445d 100644 (file)
@@ -1,3 +1,34 @@
+2014-11-11  Tim Horton  <timothy_horton@apple.com>
+
+        Occasional assertion failure under recommendedScrollbarStyleDidChange()
+        https://bugs.webkit.org/show_bug.cgi?id=138604
+        <rdar://problem/18855914>
+
+        Reviewed by Beth Dakin.
+
+        It is possible for AppKit to install tracking areas into our view
+        behind our back, but we have code that depends on knowing exactly
+        the set of tracking areas installed on WKView.
+
+        Make this more robust by keeping a reference to the tracking area we
+        use for many things and manipulating that instead of making assumptions
+        about the total set of tracking areas on WKView.
+
+        * UIProcess/API/mac/WKView.mm:
+        (-[WKView _primaryTrackingArea]):
+        (-[WKView _replacePrimaryTrackingArea:]):
+        Provide a 'primary' tracking area setter/getter.
+
+        (-[WKView initWithFrame:context:configuration:webView:]):
+        Keep a reference to the original tracking area installed at initialization time.
+
+        * UIProcess/API/mac/WKViewInternal.h:
+        * UIProcess/mac/PageClientImpl.mm:
+        (WebKit::PageClientImpl::recommendedScrollbarStyleDidChange):
+        Instead of walking the set of tracking areas, make use of the fact that
+        we know exactly which tracking area we installed, and uninstall just that
+        one, and replace it with our newly-built one.
+
 2014-11-11  Myles C. Maxfield  <mmaxfield@apple.com>
 
         Finish moving CTFontGetVerticalGlyphsForCharacters and CTLineCreateWithUniCharProvider out from WKSI
index 2f740f7..6d5c895 100644 (file)
@@ -170,6 +170,8 @@ struct WKViewInterpretKeyEventsParameters {
     RetainPtr<WKBrowsingContextController> _browsingContextController;
 #endif
 
+    RetainPtr<NSTrackingArea> _primaryTrackingArea;
+
     // For ToolTips.
     NSToolTipTag _lastToolTipTag;
     id _trackingRectOwner;
@@ -3493,6 +3495,18 @@ static NSString *pathWithUniqueFilenameForPath(NSString *path)
     return _data->_page->suppressVisibilityUpdates();
 }
 
+- (NSTrackingArea *)_primaryTrackingArea
+{
+    return _data->_primaryTrackingArea.get();
+}
+
+- (void)_setPrimaryTrackingArea:(NSTrackingArea *)trackingArea
+{
+    [self removeTrackingArea:_data->_primaryTrackingArea.get()];
+    _data->_primaryTrackingArea = trackingArea;
+    [self addTrackingArea:trackingArea];
+}
+
 - (instancetype)initWithFrame:(NSRect)frame context:(WebContext&)context configuration:(WebPageConfiguration)webPageConfiguration webView:(WKWebView *)webView
 {
     self = [super initWithFrame:frame];
@@ -3510,14 +3524,10 @@ static NSString *pathWithUniqueFilenameForPath(NSString *path)
     else
         options |= NSTrackingActiveInKeyWindow;
 
-    NSTrackingArea *trackingArea = [[NSTrackingArea alloc] initWithRect:frame
-                                                                options:options
-                                                                  owner:self
-                                                               userInfo:nil];
-    [self addTrackingArea:trackingArea];
-    [trackingArea release];
-
     _data = [[WKViewData alloc] init];
+    _data->_primaryTrackingArea = adoptNS([[NSTrackingArea alloc] initWithRect:frame options:options owner:self userInfo:nil]);
+    [self addTrackingArea:_data->_primaryTrackingArea.get()];
+
     _data->_pageClient = std::make_unique<PageClientImpl>(self, webView);
     _data->_page = context.createWebPage(*_data->_pageClient, WTF::move(webPageConfiguration));
     _data->_page->setAddsVisitedLinks(context.historyClient().addsVisitedLinks());
index 8e26b28..bb61793 100644 (file)
@@ -133,4 +133,6 @@ struct WebPageConfiguration;
 
 - (void)_dismissActionMenuPopovers;
 
+@property (nonatomic, retain, setter=_setPrimaryTrackingArea:) NSTrackingArea *_primaryTrackingArea;
+
 @end
index 68beebe..b50f27a 100644 (file)
@@ -585,13 +585,6 @@ void PageClientImpl::recordAutocorrectionResponse(AutocorrectionResponseType res
 
 void PageClientImpl::recommendedScrollbarStyleDidChange(int32_t newStyle)
 {
-    NSArray *trackingAreas = [m_wkView trackingAreas];
-    NSUInteger count = [trackingAreas count];
-    ASSERT(count == 1);
-    
-    for (NSUInteger i = 0; i < count; ++i)
-        [m_wkView removeTrackingArea:[trackingAreas objectAtIndex:i]];
-
     // Now re-create a tracking area with the appropriate options given the new scrollbar style
     NSTrackingAreaOptions options = NSTrackingMouseMoved | NSTrackingMouseEnteredAndExited | NSTrackingInVisibleRect;
     if (newStyle == NSScrollerStyleLegacy)
@@ -599,12 +592,8 @@ void PageClientImpl::recommendedScrollbarStyleDidChange(int32_t newStyle)
     else
         options |= NSTrackingActiveInKeyWindow;
 
-    NSTrackingArea *trackingArea = [[NSTrackingArea alloc] initWithRect:[m_wkView frame]
-                                                                options:options
-                                                                  owner:m_wkView
-                                                               userInfo:nil];
-    [m_wkView addTrackingArea:trackingArea];
-    [trackingArea release];
+    RetainPtr<NSTrackingArea> trackingArea = adoptNS([[NSTrackingArea alloc] initWithRect:[m_wkView frame] options:options owner:m_wkView userInfo:nil]);
+    [m_wkView _setPrimaryTrackingArea:trackingArea.get()];
 }
 
 void PageClientImpl::intrinsicContentSizeDidChange(const IntSize& intrinsicContentSize)