Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(402)

Unified Diff: third_party/WebKit/Source/core/html/HTMLAnchorElement.cpp

Issue 2043863003: Speculatively launch Service Workers on mouse/touch events. [1/5] (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: incorporated falken's comment Created 4 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: third_party/WebKit/Source/core/html/HTMLAnchorElement.cpp
diff --git a/third_party/WebKit/Source/core/html/HTMLAnchorElement.cpp b/third_party/WebKit/Source/core/html/HTMLAnchorElement.cpp
index eccde4647c675b1b06ae3b1f500fc036e4c5ac65..c483edee14a228b26ca2c5018a989c4ca8d28215 100644
--- a/third_party/WebKit/Source/core/html/HTMLAnchorElement.cpp
+++ b/third_party/WebKit/Source/core/html/HTMLAnchorElement.cpp
@@ -35,13 +35,85 @@
#include "core/loader/FrameLoaderClient.h"
#include "core/loader/PingLoader.h"
#include "core/page/ChromeClient.h"
+#include "platform/RuntimeEnabledFeatures.h"
#include "platform/network/NetworkHints.h"
+#include "platform/weborigin/SchemeRegistry.h"
#include "platform/weborigin/SecurityPolicy.h"
+#include "public/platform/WebNavigationHintType.h"
namespace blink {
using namespace HTMLNames;
+class HTMLAnchorElement::NavigationHintSender : public GarbageCollected<HTMLAnchorElement::NavigationHintSender> {
+public:
+ static NavigationHintSender* create(HTMLAnchorElement* anchorElement)
+ {
+ return new NavigationHintSender(anchorElement);
+ }
+ void handleEvent(Event*);
+
+ DECLARE_VIRTUAL_TRACE();
+
+private:
+ explicit NavigationHintSender(HTMLAnchorElement*);
+ bool shouldSendNavigationHintForServiceWorker() const;
+ void maybeSendNavigationHintForServiceWorker(WebNavigationHintType);
+
+ Member<HTMLAnchorElement> m_anchorElement;
+};
+
+void HTMLAnchorElement::NavigationHintSender::handleEvent(Event* event)
+{
+ if (event->type() == EventTypeNames::mousedown && event->isMouseEvent() && toMouseEvent(event)->button() == LeftButton)
+ maybeSendNavigationHintForServiceWorker(WebNavigationHintType::LinkMouseDown);
+ else if (event->type() == EventTypeNames::gesturetapunconfirmed)
+ maybeSendNavigationHintForServiceWorker(WebNavigationHintType::LinkTapUnconfirmed);
+ else if (event->type() == EventTypeNames::gestureshowpress)
+ maybeSendNavigationHintForServiceWorker(WebNavigationHintType::LinkTapDown);
+}
+
+DEFINE_TRACE(HTMLAnchorElement::NavigationHintSender)
+{
+ visitor->trace(m_anchorElement);
+}
+
+HTMLAnchorElement::NavigationHintSender::NavigationHintSender(HTMLAnchorElement* anchorElement)
+ : m_anchorElement(anchorElement)
+{
+}
+
+bool HTMLAnchorElement::NavigationHintSender::shouldSendNavigationHintForServiceWorker() const
+{
+ const KURL& url = m_anchorElement->href();
+ if (!SchemeRegistry::shouldTreatURLSchemeAsAllowingServiceWorkers(url.protocol()))
+ return false;
+ Document& document = m_anchorElement->document();
+ if (!document.frame())
+ return false;
+ if (!document.getSecurityOrigin()->canDisplay(url))
+ return false;
falken 2016/06/15 13:48:19 I'm probably just clueless about DOM stuff but why
horo 2016/06/16 06:02:44 Added comment about checking frame(). Ah we don't
+ if (url.hasFragmentIdentifier() && equalIgnoringFragmentIdentifier(document.url(), url))
+ return false;
falken 2016/06/15 13:48:19 Thanks for the explanation of this one, that makes
+
+ // If the opener is to be suppressed and the target frame name is set,
+ // WebContentsImpl::CreateNewWindow() will create a new process when the
+ // user click the anchor element. In such case we shouldn't start the
falken 2016/06/15 13:48:19 s/click/clicks
+ // Service Worker not to keep the current process running.
falken 2016/06/15 13:48:19 The first sentence makes sense to me, but the seco
horo 2016/06/16 06:02:44 I thought that we should not run the SW in the cur
+ const bool openerSuppressed = m_anchorElement->hasRel(RelationNoReferrer) || m_anchorElement->hasRel(RelationNoOpener);
+ if (openerSuppressed && !m_anchorElement->getAttribute(targetAttr).isEmpty())
+ return false;
+ return true;
+}
+
+void HTMLAnchorElement::NavigationHintSender::maybeSendNavigationHintForServiceWorker(WebNavigationHintType type)
+{
+ if (!shouldSendNavigationHintForServiceWorker())
+ return;
+
+ // TODO(horo): Send the navigation hint message to the browser process.
+}
+
HTMLAnchorElement::HTMLAnchorElement(const QualifiedName& tagName, Document& document)
: HTMLElement(tagName, document)
, m_linkRelations(0)
@@ -59,6 +131,12 @@ HTMLAnchorElement::~HTMLAnchorElement()
{
}
+DEFINE_TRACE(HTMLAnchorElement)
+{
+ visitor->trace(m_navigationHintsender);
+ HTMLElement::trace(visitor);
+}
+
bool HTMLAnchorElement::supportsFocus() const
{
if (hasEditableStyle())
@@ -162,6 +240,10 @@ void HTMLAnchorElement::defaultEventHandler(Event* event)
return;
}
+ // TODO(horo): Call NavigationHintSender::handleEvent() when
+ // SpeculativeLaunchServiceWorker feature is enabled.
+ // ensureNavigationHintSender()->handleEvent(event);
+
if (isLinkClick(event) && isLiveLink()) {
handleClick(event);
return;
@@ -396,4 +478,11 @@ Node::InsertionNotificationRequest HTMLAnchorElement::insertedInto(ContainerNode
return request;
}
+HTMLAnchorElement::NavigationHintSender* HTMLAnchorElement::ensureNavigationHintSender()
+{
+ if (!m_navigationHintsender)
+ m_navigationHintsender = NavigationHintSender::create(this);
+ return m_navigationHintsender;
+}
+
} // namespace blink

Powered by Google App Engine
This is Rietveld 408576698