반응형
페이지 스크롤에서 활성 메뉴 항목을 변경하시겠습니까?
페이지를 스크롤하면 활성 메뉴 항목이 바뀝니다.어떻게 하는 겁니까?
컨테이너의 스크롤 이벤트(일반적으로 윈도우)에 바인딩하여 수행합니다.
간단한 예:
// Cache selectors
var topMenu = $("#top-menu"),
topMenuHeight = topMenu.outerHeight()+15,
// All list items
menuItems = topMenu.find("a"),
// Anchors corresponding to menu items
scrollItems = menuItems.map(function(){
var item = $($(this).attr("href"));
if (item.length) { return item; }
});
// Bind to scroll
$(window).scroll(function(){
// Get container scroll position
var fromTop = $(this).scrollTop()+topMenuHeight;
// Get id of current scroll item
var cur = scrollItems.map(function(){
if ($(this).offset().top < fromTop)
return this;
});
// Get the id of the current element
cur = cur[cur.length-1];
var id = cur && cur.length ? cur[0].id : "";
// Set/remove active class
menuItems
.parent().removeClass("active")
.end().filter("[href='#"+id+"']").parent().addClass("active");
});
스크롤 애니메이션을 포함하여 jsFiddle에서 위의 내용을 확인할 수 있습니다.
내 코드와 스나이퍼를 확인하고 데모 링크를 클릭하면 됩니다.
// Basice Code keep it
$(document).ready(function () {
$(document).on("scroll", onScroll);
//smoothscroll
$('a[href^="#"]').on('click', function (e) {
e.preventDefault();
$(document).off("scroll");
$('a').each(function () {
$(this).removeClass('active');
})
$(this).addClass('active');
var target = this.hash,
menu = target;
$target = $(target);
$('html, body').stop().animate({
'scrollTop': $target.offset().top+2
}, 500, 'swing', function () {
window.location.hash = target;
$(document).on("scroll", onScroll);
});
});
});
// Use Your Class or ID For Selection
function onScroll(event){
var scrollPos = $(document).scrollTop();
$('#menu-center a').each(function () {
var currLink = $(this);
var refElement = $(currLink.attr("href"));
if (refElement.position().top <= scrollPos && refElement.position().top + refElement.height() > scrollPos) {
$('#menu-center ul li a').removeClass("active");
currLink.addClass("active");
}
else{
currLink.removeClass("active");
}
});
}
$(document).ready(function () {
$(document).on("scroll", onScroll);
//smoothscroll
$('a[href^="#"]').on('click', function (e) {
e.preventDefault();
$(document).off("scroll");
$('a').each(function () {
$(this).removeClass('active');
})
$(this).addClass('active');
var target = this.hash,
menu = target;
$target = $(target);
$('html, body').stop().animate({
'scrollTop': $target.offset().top+2
}, 500, 'swing', function () {
window.location.hash = target;
$(document).on("scroll", onScroll);
});
});
});
function onScroll(event){
var scrollPos = $(document).scrollTop();
$('#menu-center a').each(function () {
var currLink = $(this);
var refElement = $(currLink.attr("href"));
if (refElement.position().top <= scrollPos && refElement.position().top + refElement.height() > scrollPos) {
$('#menu-center ul li a').removeClass("active");
currLink.addClass("active");
}
else{
currLink.removeClass("active");
}
});
}
body, html {
margin: 0;
padding: 0;
height: 100%;
width: 100%;
}
.menu {
width: 100%;
height: 75px;
background-color: rgba(0, 0, 0, 1);
position: fixed;
background-color:rgba(4, 180, 49, 0.6);
-webkit-transition: all 0.4s ease;
-moz-transition: all 0.4s ease;
-o-transition: all 0.4s ease;
transition: all 0.4s ease;
}
.light-menu {
width: 100%;
height: 75px;
background-color: rgba(255, 255, 255, 1);
position: fixed;
background-color:rgba(4, 180, 49, 0.6);
-webkit-transition: all 0.4s ease;
-moz-transition: all 0.4s ease;
-o-transition: all 0.4s ease;
transition: all 0.4s ease;
}
#menu-center {
width: 980px;
height: 75px;
margin: 0 auto;
}
#menu-center ul {
margin: 0 0 0 0;
}
#menu-center ul li a{
padding: 32px 40px;
}
#menu-center ul li {
list-style: none;
margin: 0 0 0 -4px;
display: inline;
}
.active, #menu-center ul li a:hover {
font-family:'Droid Sans', serif;
font-size: 14px;
color: #fff;
text-decoration: none;
line-height: 50px;
background-color: rgba(0, 0, 0, 0.12);
padding: 32px 40px;
}
a {
font-family:'Droid Sans', serif;
font-size: 14px;
color: black;
text-decoration: none;
line-height: 72px;
}
#home {
background-color: #286090;
height: 100vh;
width: 100%;
overflow: hidden;
}
#portfolio {
background: gray;
height: 100vh;
width: 100%;
}
#about {
background-color: blue;
height: 100vh;
width: 100%;
}
#contact {
background-color: rgb(154, 45, 45);
height: 100vh;
width: 100%;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<!-- <div class="container"> --->
<div class="m1 menu">
<div id="menu-center">
<ul>
<li><a class="active" href="#home">Home</a>
</li>
<li><a href="#portfolio">Portfolio</a>
</li>
<li><a href="#about">About</a>
</li>
<li><a href="#contact">Contact</a>
</li>
</ul>
</div>
</div>
<div id="home"></div>
<div id="portfolio"></div>
<div id="about"></div>
<div id="contact"></div>
@Marcus Ekwall의 답변을 보완하기 위해서입니다.이렇게 하면 앵커 링크만 얻을 수 있습니다.그리고 앵커 링크와 일반적인 링크가 섞여 있다면 문제가 없을 것입니다.
jQuery(document).ready(function(jQuery) {
var topMenu = jQuery("#top-menu"),
offset = 40,
topMenuHeight = topMenu.outerHeight()+offset,
// All list items
menuItems = topMenu.find('a[href*="#"]'),
// Anchors corresponding to menu items
scrollItems = menuItems.map(function(){
var href = jQuery(this).attr("href"),
id = href.substring(href.indexOf('#')),
item = jQuery(id);
//console.log(item)
if (item.length) { return item; }
});
// so we can get a fancy scroll animation
menuItems.click(function(e){
var href = jQuery(this).attr("href"),
id = href.substring(href.indexOf('#'));
offsetTop = href === "#" ? 0 : jQuery(id).offset().top-topMenuHeight+1;
jQuery('html, body').stop().animate({
scrollTop: offsetTop
}, 300);
e.preventDefault();
});
// Bind to scroll
jQuery(window).scroll(function(){
// Get container scroll position
var fromTop = jQuery(this).scrollTop()+topMenuHeight;
// Get id of current scroll item
var cur = scrollItems.map(function(){
if (jQuery(this).offset().top < fromTop)
return this;
});
// Get the id of the current element
cur = cur[cur.length-1];
var id = cur && cur.length ? cur[0].id : "";
menuItems.parent().removeClass("active");
if(id){
menuItems.parent().end().filter("[href*='#"+id+"']").parent().addClass("active");
}
})
})
기본적으로 교체했습니다.
menuItems = topMenu.find("a"),
타고
menuItems = topMenu.find('a[href*="#"]'),
모든 링크를 어딘가에 있는 앵커와 연결하고, 이것을 작동시키기 위해 필요한 모든 것을 변경하는 것.
jsfiddle에서 실행 중 보기
JQuery 3에서 수락된 답변을 작동시키려면 다음과 같이 코드를 변경합니다.
var scrollItems = menuItems.map(function () {
var id = $(this).attr("href");
try {
var item = $(id);
if (item.length) {
return item;
}
} catch {}
});
javascript가 해당 id에 의해 요소가 없을 경우 충돌하지 않도록 try-catch도 추가하였습니다.조금이라도 더 발전시켜보세요 ;)
언급URL : https://stackoverflow.com/questions/9979827/change-active-menu-item-on-page-scroll
반응형
'programing' 카테고리의 다른 글
| MySQL Workbench EER 다이어그램 테이블 색상 변경 (0) | 2023.10.29 |
|---|---|
| sqlddeveloper의 여러 오라클 연결에서 쿼리 (0) | 2023.10.29 |
| 유사 TTY 할당을 위한 Docker-t 옵션에 대해 혼동함 (0) | 2023.10.24 |
| PlayStore Developer Console에서 '베타로 롤아웃 시작'이 비활성화됨 (0) | 2023.10.24 |
| HTML/CSS에서 이미지의 일부만 표시하려면 어떻게 해야 합니까? (0) | 2023.10.24 |