Add "Active" class to current link plugin Toc

I try to add an “active” class to each link of my Table of Contents

The snippet Toc is :

<?php foreach($headlines as $headline): ?>
         <a class="<?= $idd === $headline ? 'active' : '' ?>" href="<?= $page->url() . '/#' . Str::slug(str::unhtml($headline->text())) ?>"><?= $headline->text() ?></a>
<?php endforeach ?>

The template is :

<?php snippet('toc', ['headlines' => $page->text()->headlines('h2')]) ?>

The controller is :

return function ($page) {
    $idd = $page->id();
    return [
        'idd' => $idd,

Any recommendations? Thanks!

Are you using the headlines() field method as in the cookbook recipe here Of anchors and ToCs, part 1 | Kirby CMS?

Using the $page->id() somehow doesn’t make sense because that’s always the same and has nothing to do with your headlines.

So you would have to check the URL for currently active headline (and $headline in case you are using said field method is an object with 3 props (url, text, id), anyway).

The problem is that you cannot get the hash server-side, so you need some JavaScript here.

Yes I’m using the headlines() field method as in the cookbook

Ok I’ll try this one MenuSpy


I think there is a simple way to do that with some JS :

  $('.clicks li').on('click', function(){


  <?php foreach($headlines as $headline): ?>
            <a href="<?= $page->url() . '/#' . Str::slug(str::unhtml($headline->text())) ?>"><?= $headline->text() ?></a>
      <?php endforeach ?>

So it works on the <li> but if I replace '.clicks li' by '.clicks li a' the .active is removed only if I click a second time on the <a> , is there a way to make it working ? Or should I found an other way ?


If you replace '.clicks li'´ with .clicks li a, then siblings() will not longer work, as the other a elements inside the li elements are not the siblings?

Thank you for putting me on the right path ! :slight_smile:

  $('.clicks li a').on('click', function(){
    $('.clicks li a').not(this).removeClass('actived');