Active menu item from a structure field

I’m trying to create a different way to add pages (and other URLS) to a menu with a structure field but I’m struggling with adding an active class to the list element with the current page url using the Kirby Link Field plugin (@hdodov). Is this possible?

I’ve tried the following but this gives every li a class of active.

<?php foreach ($site->pagesInMenu()->toStructure() as $menuItem): ?>
   <li <?php e($menuItem->isActive(), ' class="active"') ?>> <a href="<?= $menuItem->menuItemURL()->toLinkObject() ?>"><?= $menuItem->menuItemText() ?></a></li>
<?php endforeach ?>

$menuItem in this case is a structureObject, which cannot be active. isActive() is a page method that requires a page object.

I’m not sure what $menuItem->menuItemURL()->toLinkObject() actually returns in the different cases, i.e. if the link is a page, a file, a url string.

That would be interesting to know.

My guess is that you get a page object in case of a page link, but of course not for other link types.

In any case, you would only be able to use isActive() if you have a page object and this wouldn’t work for other types of urls.

In that case, you would instead have to compare the current url against the menu item url, something like

<li <?php e($_SERVER['REQUEST_URI'] === $menuItem->menuItemURL()->toLinkObject()->url(), ' class="active"') ?>> <a href="<?= $menuItem->menuItemURL()->toLinkObject()->url() ?>"><?= $menuItem->menuItemText() ?></a></li>

I think it returns a Link object.

It seems like one can get the Page from that by calling a $link->page() function (which might return null if the page doesn’t exist or the link isn’t a page), so I guess a way to get to isActive could be:

<?php 
  e($menuItem->menuItemURL()->toLinkObject()->page()?->isActive(), 'class="active"')
?>

Hi Sonja, Thanks for your reply.

If the menu item is a page it should become active when you visit it.
If the item is a different url or a file it opens in a new tab (so no need for becoming active).

I fixed it by creating a variable

$actual_link = "http://$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]"; 

And

<li <?php e($actual_link === $menuItem->menuItemURL()->toLinkObject()->url(), ' class="active"') ?>> <a href="<?= $menuItem->menuItemURL()->toLinkObject()->url() ?>"><?= $menuItem->menuItemText() ?></a></li>

Which is working but do you think it’s a good solution or do you see some potential threats?

What @rasteiner suggested above is probably the best option, given that you only need the active class for pages.