I have set up a WP menu in Appearance > Menus which contains some links to pages on the site (Home, Tour, Contact), and some “Custom Link” anchors to scroll to IDs on the home page. E.g. “/#music” and “/#videos”. So sort of a hybrid one-pager site. I have set an “Active” color (Nav Menu widget > Top level > Active Typography) which in this case is red, to indicate to the user the current page they are on (e.g. Home is red on the home page, Contact is red on the Contact page)
Please forgive me if this not a bug and I’m just missing something here. When I am on the Home page, which contains the #music, #videos and #subscribe elements, the menu is showing active/red on Home, Music, Videos, Subscribe all at the same time. This presents as weird and broken to me. I am thinking this might be a bug because I cannot imagine anyone would want this. I don’t recall experiencing it in other builders/themes or websites that I’ve visited. I’d expect normal behaviour to just have Home as active (the current page) and leave it at that, or dynamically change colors as you scroll (not expecting Bricks to do this - it would be nice, but I can achieve this with a 3rd party plugin).
It seems it is active for the page you are on. The anchor links are all on the same page so it will show the menu item active for any anchor link you choose on that page.
In my experience with other builders and themes and browsing websites over the years, anchor links which scroll to part of the page shouldn’t be their active color until you are on that section of the page or you click on them. Elementor works perfectly like this, as do popular themes I’ve used. Instead Bricks just lights up all anchor links as active at the same time before you even click on anything and they stay like that. It’s a weird user experience that makes no sense to me.
Submenu links will not change colors either. The top level link, even if it does not go to a page, will change colors if a submenu link is clicked, but the submenu link itself won’t.
This is actually only a few lines of javascript code to make it work. I have my own javacode for the nestable nav menu so the submenu links work. If I had time, I would make the the anchor links work.
Email help@bricksbuilder.io and complain about it. Tell them we want submenu links to change colors too.
I never mentioned submenu links. I don’t think I’ve communicated the issue to you very well. Hopefully the Bricks team understand what Matt Eastwood and myself are referring to. Currently if you want normal behaviour from a main menu with anchor links you need to go install a 3rd party plugin or add custom JS. Which I have done. But it would be good for the future to get this usable.
I fully understand what you are saying. I am also saying, along with your desire for only the anchor link that is clicked to change color, the desire for submenu links to change color is needed too.
I can replicate the issue. However, it’s more of an improvement than a bug because there is no code to provide the desired behavior. So I created an improvement task for it.
If the problem still exists. Unfortunately, Bricks does not set a class for active navigation elements, which is a real omission. Hopefully it will be fixed soon. Until then you can create them yourself with a JavaScript code.
First of all, please excuse my bad English. Assuming you use the standard navigation (the old one) and a template for the header (but it should also work if you integrate the navigation menu directly into the one-pager).
first, of course, you should set up your one-pager menu properly so that it works.
in the next step, add the following JavaScript under Bricks/ Settings / Custom Code / Header Scripts (make sure that your own scripts are allowed - Same Settings Page → Enable code execution).
<script>document.addEventListener('DOMContentLoaded', function () {
const navLinks = document.querySelectorAll('.menu-item');
navLinks.forEach(link => {
link.addEventListener('click', function () {
// Remove the 'active-link' class from all links
navLinks.forEach(link => link.classList.remove('active-link'));
// Add the 'active-link' class to the clicked link
this.classList.add('active-link');
});
});
});</script>
The script adds another class called .active-link to the clicked active element with the .menu-item class.
You can now address this class via CSS, e.g. .active-link a {color: #FFFF00!important;}. The Important may be required, depending on how specifically you define the class.
I just did it successfully on my site, so I can post it here quickly. I hope it works for you!
Does anyone know if this issue has been resolved in Bricks or if there is an alternate fix to it?
The js provided above seems to be working in the sense that now the active link (#anchor) is the same colour as all the other menu nav items but it seems that there is another class with more specificity and not allowing it change to alternate colour. This is frustrating because if you navigate to another page then that active page/link does not change colour in the nav menu either…
Dont forget, if your section is too big, than add ID to something smaller for you anchor.
Hope this will help you.
<script>
document.addEventListener('DOMContentLoaded', function () {
const navLinks = document.querySelectorAll('.menu-item a');
const sections = [];
// Create an array of sections corresponding to each nav link
navLinks.forEach(link => {
const section = document.querySelector(link.getAttribute('href'));
if (section) {
sections.push({
link: link,
section: section,
});
}
});
// Function to remove 'active-link' class from all links
function removeActiveClass() {
navLinks.forEach(link => {
link.parentElement.classList.remove('active-link');
});
}
// Create Intersection Observer with lower thresholds for better section tracking
const observer = new IntersectionObserver((entries) => {
entries.forEach(entry => {
if (entry.isIntersecting) {
removeActiveClass();
// Add active-link class to the visible section's link
const activeLink = document.querySelector(`a[href="#${entry.target.id}"]`);
if (activeLink) {
activeLink.parentElement.classList.add('active-link');
}
}
});
}, {
threshold: [0.1, 0.25, 0.5] // Lower thresholds to trigger earlier for large sections
});
// Observe each section
sections.forEach(({ section }) => {
observer.observe(section);
});
// Smooth scroll to anchor links
navLinks.forEach(link => {
link.addEventListener('click', function (e) {
e.preventDefault(); // Prevent default anchor behavior
removeActiveClass(); // Remove active-link class from all links
this.parentElement.classList.add('active-link'); // Add active class to the clicked link
const targetId = this.getAttribute('href').substring(1);
const targetSection = document.getElementById(targetId);
// Scroll smoothly to the section
window.scrollTo({
top: targetSection.offsetTop - 50, // Adjust for fixed headers
behavior: 'smooth'
});
// Manually check the section after scrolling
setTimeout(() => {
observer.takeRecords(); // Force observer to check current visibility
}, 300); // Add a delay to ensure scroll is completed
});
});
// Add a scroll listener to force a check when scrolling ends
let isScrolling;
window.addEventListener('scroll', function () {
window.clearTimeout(isScrolling);
isScrolling = setTimeout(function() {
observer.takeRecords(); // Re-check sections after scrolling stops
}, 200);
});
});
</script>
Hello Matej, I am not sure, if this is in production already? I expect to change the active link on scroll, but it isn’t. How can I set it up properly?
The solution with Bricks should work on click and on page refresh, but not on scroll. So I’m glad that you found a solution with that snippet - it looks like it works perfectly for your case.
Besides the anchor link part, when using the nestable nav menu, all my links remain in the active state even using different urls. Take a look below if possible.
Didn’t try it because it will screw me up a little. It is an assumption.
Basically, when we set the template mode to “content”, we stay in the account page and the sub-pages are loaded as content inside a block. But, the url is changed normally (that is its advantage).