// Copyright 2018 The Chromium Authors // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #ifndef THIRD_PARTY_BLINK_RENDERER_CORE_HTML_ANCHOR_ELEMENT_METRICS_SENDER_H_ #define THIRD_PARTY_BLINK_RENDERER_CORE_HTML_ANCHOR_ELEMENT_METRICS_SENDER_H_ #include <compare> #include "third_party/blink/public/mojom/loader/navigation_predictor.mojom-blink.h" #include "third_party/blink/public/mojom/preloading/anchor_element_interaction_host.mojom-blink.h" #include "third_party/blink/renderer/core/core_export.h" #include "third_party/blink/renderer/core/frame/local_frame_view.h" #include "third_party/blink/renderer/platform/allow_discouraged_type.h" #include "third_party/blink/renderer/platform/heap/collection_support/heap_hash_set.h" #include "third_party/blink/renderer/platform/heap/garbage_collected.h" #include "third_party/blink/renderer/platform/mojo/heap_mojo_remote.h" #include "third_party/blink/renderer/platform/supplementable.h" #include "third_party/blink/renderer/platform/wtf/vector.h" namespace blink { class Document; class HTMLAnchorElement; class IntersectionObserver; class IntersectionObserverEntry; class PointerEvent; // AnchorElementMetricsSender is responsible to send anchor element metrics to // the browser process for a given document. // // AnchorElementMetricsSenders are created for documents in main frames. Any // same-origin iframes reuse the AnchorElementMetricsSender of their main frame. // Cross-origin iframes do not use any AnchorElementMetricsSender. // // The high level approach is: // 1) When HTMLAnchorElements are inserted into the DOM, // AnchorElementMetricsSender::AddAnchorElement is called and a reference to // the element is stored. The first time this happens, the sender is created, // which registers itself for lifecycle callbacks. // 2) If any elements enter the viewport, the intersection observer will call // AnchorElementMetricsSender::UpdateVisibleAnchors. Elements are collected // in entered_viewport_messages_ and will be reported after the next layout. // 3) On the next layout, AnchorElementMetricsSender::DidFinishLifecycleUpdate // is called, and it goes over the collected anchor elements. Elements that // are visible are reported to the browser via ReportNewAnchorElements. We // also may add an element to the intersection observer that watches for // elements entering/leaving the viewport. The anchor elements collected in // AnchorElementMetricsSender are all dropped. In particular, this drops // elements that are not visible. They will never be reported even if they // become visible later, unless the are reinserted into the DOM. This is not // ideal, but simpler, keeps resource usage low, and seems to work well // enough on the sites I've looked at. Also, elements that entered the // viewport will be reported using ReportAnchorElementsEnteredViewport. We // stop observing lifecycle changes until the next anchor being added or // entering/existing the viewport, when we again wait for the next layout. class CORE_EXPORT AnchorElementMetricsSender final : public GarbageCollected<AnchorElementMetricsSender>, public LocalFrameView::LifecycleNotificationObserver, public Supplement<Document> { … }; } // namespace blink #endif // THIRD_PARTY_BLINK_RENDERER_CORE_HTML_ANCHOR_ELEMENT_METRICS_SENDER_H_