javascript - 单页导航出现问题 - 更新/突出显示事件状态并滚动到 anchor

标签 javascript jquery html css

我已经忙于一页导航。您将在下面找到有关该问题和我的愿望的更多信息。

它应该如何运作?

单击导航项后,滚动到其特定部分并更新菜单的事件类。如果页面滚动到它的特定部分,它也应该更新事件状态 - 所以将类更改为它的特定 anchor 。

固定标题

对于网站,我还使用了固定标题,因此不应覆盖特定部分。因此,当标题底部到达该部分的顶部时,菜单应该停止滚动。

可变部分

同一页面设计中的所有部分都有不同的高度。

问题

我已经尝试了很多代码,让它工作。大多数代码都可以工作,但这在所有浏览器中都不一样。此外,我在更新特定部分的事件状态时遇到了一些麻烦 - 与事件 anchor 匹配。

代码

我使用 jQuery 创建了一个平滑的 anchor 滚动。 You can see my working code at JSfiddle .

这里是所有资源:

JS

这里我控制了导航的点击功能。 所以当用户点击 #primary-navwrapper 的列表项时,然后更改事件状态类并滚动到与单击的 anchor 匹配的特定部分。

$('#primary-navwrapper li').find('a[href^="#"]').click(function(event) { 
    // Prevent from default action to intitiate
    event.preventDefault();


    $('#primary-navwrapper li a').removeClass("current");
    $(this).addClass("current");


    // The id of the section we want to go to.
    var anchorId = $(this).attr("href");
    
    // Our scroll target : the top position of the
    // section that has the id referenced by our href.
    var target = $(anchorId).offset().top - offset;
    //console.log(target);
    
    
    $('html, body').animate({ scrollTop: target }, 500, function () {
        //window.location.hash = '!' + id;
        window.location.hash = anchorId;        
    });
    

});

除了点击功能,我还希望当用户滚动一页时,它会自动更新事件语句。

function setActiveListElements(event){
    // Get the offset of the window from the top of page
    var windowPos = $(window).scrollTop();
    
    $('#primary-navwrapper li a[href^="#"]').each(function() { 
        var anchorId = $(this);
        var target = $(anchorId.attr("href"));
        
        if (target.length > 0) {
            if (target.position().top <= windowPos && target.position().top + target.height() > windowPos) {
                $('#primary-navwrapper li a').removeClass("current");
                anchorId.addClass("current");
            }
        }
    });
}

$(window).scroll(function() {
    setActiveListElements();
});

在上面的代码中,我认为 if (target.position().top <= windowPos && target.position().top + target.height() > windowPos) 这一行不正确,可能太长了..

如果有任何问题或其他问题,我希望收到您的来信。 卡斯帕

最佳答案

查看您的代码,我已经更新了您为以下代码所说的行:

if (target.position().top - $('#header').outerHeight() <= windowPos) {
    $('#primary-navwrapper li a').removeClass("current");
    anchorId.addClass("current");
}

通过这种方式,它会得到目标与顶部的差异减去标题的高度(因为它将始终可见),然后检查窗口的位置。如果它是劣质的,则用户已经通过了这个 anchor ,因此菜单中的相应链接会突出显示。

而且您的第一个链接在 fiddle 中没有 anchor ,因此:

<li><a href="#hero" class="current">Home</a></li>

在这些更改之后,一切似乎都运行良好。

JSFiddle:http://jsfiddle.net/8n06pvy9/17/

编辑:
为了更新哈希,我尝试使用简单的 window.location.hash = anchorId;,但它会导致 FF 和 IE 中出现一些奇怪的滚动问题。我花了一些时间研究它,但我无法弄清楚会发生什么。

因此,我建议使用一个我已经使用过的技巧,在散列中使用 #!。这样,您的代码将是这样的:

window.location.hash = '#!' + anchorId.replace('#', '');

在滚动函数中,像这样:

window.location.hash = '#!' + anchorId.attr('href').replace('#', '');

JSFiddle:http://jsfiddle.net/8n06pvy9/18/

而且,如果需要,您可以检查页面加载中的散列,删除感叹号并将页面滚动到所需的 anchor 。或者,如果你想避免所有这些,你总是可以使用一些历史插件,比如 this one .对于您的情况,我个人不会为此使用插件,但是否值得由您决定。

希望对您有所帮助!

关于javascript - 单页导航出现问题 - 更新/突出显示事件状态并滚动到 anchor ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28678548/

相关文章:

html - 持久性页眉和页脚

javascript - 延迟加载集合时如何获取获取的模型?

javascript - 如何使用正则表达式来测试具有特殊字符的文件名

Jquery爆炸效果不起作用

计算器中的 Javascript 乘法问题

java - 是否存在用于单元测试的 assertHTMLEquals 之类的东西

javascript - JavaScript 是一种按引用传递还是按值传递的语言?

javascript - 使用 Javascript 将棘手的字符串替换为 2 个字符串组合

javascript - 将 Jquery 添加到 Vue-Cli 3

javascript - 尝试在 Chrome 中使用 jQuery 同步 AJAX + .ready() 时出现不可预测的行为