Skip to content

Track Anchor Clicks

Same-page anchor links — <a href="#section-3"> — are used in tables of contents, FAQ accordions, and long-form documentation. Tracking these clicks reveals which sections users want to jump to directly, indicating which content is most important to them.

GTM can detect anchor link clicks using a trigger condition that matches href values starting with #.

  1. Enable Click Variables

    In GTM → Variables → Configure, enable:

    • Click URL
    • Click Text
    • Click Element
    • Click ID
  2. Create a Click Trigger for Anchor Links

    • Trigger type: Click – Just Links
    • Fire on: Some Link Clicks
    • Condition: Click URL matches RegEx #[^/]

    This matches any link URL that contains # followed by at least one non-slash character.

    Alternatively, use: Click URL contains # AND Click URL does not equal {{Page URL}}

  3. Create a Custom JavaScript Variable for the anchor destination

    Variable Click - Anchor Target:

    function() {
    var url = `{{Click URL}}`;
    var hash = url ? url.split('#')[1] : undefined;
    return hash || undefined;
    }
  4. Create a GA4 Event Tag

    • Tag type: Google Analytics: GA4 Event
    • Event name: anchor_click
    • Parameters:
      • anchor_destination{{Click - Anchor Target}}
      • link_text{{Click Text}}
      • page_path{{Page Path}}
    • Trigger: the anchor click trigger
  5. Test in Preview Mode

    Click a table-of-contents link. The anchor_click event should appear with the correct anchor_destination.

Tag Configuration

GA4 - anchor_click

Type
Google Analytics: GA4 Event
Trigger
Link Click - href contains #
Variables
Click - Anchor TargetClick TextPage Path

If you want to capture the title of the section being navigated to (not just its ID), use a dataLayer push from the anchor links:

dataLayer.push() anchor_click

Push when an anchor link is clicked, with the destination section's heading text.

document.querySelectorAll('a[href^="#"]').forEach(function(link) {
link.addEventListener('click', function() {
var targetId = this.getAttribute('href').substring(1);
var targetEl = document.getElementById(targetId);
// Find the heading inside the target section
var sectionTitle = null;
if (targetEl) {
var heading = targetEl.querySelector('h1, h2, h3, h4') ||
(targetEl.tagName.match(/^H[1-6]$/) ? targetEl : null);
sectionTitle = heading ? heading.textContent.trim() : null;
}
window.dataLayer = window.dataLayer || [];
window.dataLayer.push({
event: 'anchor_click',
anchor_id: targetId,
anchor_section_title: sectionTitle || targetId,
link_text: this.textContent.trim(),
page_path: window.location.pathname
});
});
});

This approach is more useful for articles where the anchor ID is a generated slug but you want the human-readable section title in GA4.

For a table of contents specifically, add context about where in the TOC the link sits:

var tocLinks = document.querySelectorAll('.table-of-contents a[href^="#"]');
tocLinks.forEach(function(link, index) {
link.addEventListener('click', function() {
window.dataLayer = window.dataLayer || [];
window.dataLayer.push({
event: 'anchor_click',
anchor_id: this.getAttribute('href').substring(1),
anchor_section_title: this.textContent.trim(),
toc_position: index + 1,
toc_total: tocLinks.length,
page_path: window.location.pathname
});
});
});

This tells you not just which section users jump to, but where it sits in the document hierarchy.

Use the anchor_section_title dimension in GA4 Explore to find your most-jumped-to sections. High anchor click rates on a section means:

  • Users who scan content look for that section specifically → make it more prominent
  • Users who land mid-article jump to it directly → consider whether a shorter path exists
  • Users re-visit that section after reading others → it may contain the decision-making information
  1. Open GTM Preview and visit a page with anchor links (a table of contents or FAQ)
  2. Click an anchor link
  3. The anchor_click event should appear in the Summary pane
  4. Verify anchor_destination or anchor_id contains the section ID (e.g., getting-started)
  5. Verify link_text shows the link label

Click URL returns the full absolute URL plus the fragment. For example, https://yoursite.com/article#section-2. Your anchor target variable must split on # and take the second part.

href="#" for toggle buttons. Some buttons and accordion toggles use href="#" as a placeholder. Your trigger will catch these too. Add a condition: Click URL does not equal {{Page URL}}# to exclude pure # anchors.

SPA hash routing. In SPAs that use hash-based routing (e.g., /#/about), the #/about would match your anchor trigger. Add a condition: Click URL does not match RegEx #/ to exclude hash routes.