我有两个div元素:
当用户滚动div #element-A
并且#header-one-target
到达包含div的顶部时,#animate-hd-b
中的最后一个元素(#element-B
)应该滚动到包含div的顶部div动画效果不错。
这是我要开始使用的代码。下面的代码在滚动窗口而不是div时会执行某些操作。
$(window).scroll(function() {
var offsetTop = $('#animate-hd-b').offset().top,
outerHeight = $('#animate-hd-b').outerHeight(),
windowHeight = $(window).height(),
scrollTop = $(this).scrollTop();
console.log((offsetTop-windowHeight) , scrollTop);
if (scrollTop > (offsetTop+outerHeight-windowHeight)){
alert('you have scrolled to the top!');
}
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="element-A" style="background: orange; overflow: auto;">
<div class="content" style="padding-bottom: 300px;">
<p>content</p>
<p>content</p>
<p>content</p>
<p>content</p>
<h1 id="header-one-target">Header One</h1>
</div>
</div>
<div id="element-B" style="background: yellow; overflow: auto;">
<div class="content" style="padding-bottom: 300px;">
<p>content</p>
<p>content</p>
<p>content</p>
<p>content</p>
<h1 id="animate-hd-b">Animate This Header</h1>
</div>
</div>
有没有办法在jQuery中做到这一点?
答案 0 :(得分:4)
这真的很简单。您只需跟踪#header-one-target
并进行动画处理
#animate-hd-b
到达顶部时,#header-one-target
。
(function($) {
let $elementA = $('#element-A');
let $elementB = $('#element-B');
let $headerOneTarget = $('#header-one-target');
let $animateHdB = $('#animate-hd-b');
let isScrollAtTop = true;
$elementA.scroll(function() {
if (isScrollAtTop && $headerOneTarget.offset().top < 5) {
isScrollAtTop = false;
$elementB.animate({
scrollTop: $elementB.scrollTop() + $animateHdB.offset().top
});
} else if ($elementA.scrollTop() < 5) {
isScrollAtTop = true;
$elementB.animate({
scrollTop: 0
});
}
});
})(jQuery);
#element-A {
background: orange;
overflow: auto;
height: 100vh;
width: 60vw;
position: fixed;
top: 0;
left: 0;
}
#element-B {
position: fixed;
top: 0;
right: 0;
height: 100vh;
width: 40vw;
background: yellow;
overflow: auto;
}
.content {
padding: 10px;
}
.content-vh100 {
height: 100vh;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="element-A">
<div class="content">
<p>Scroll</p>
<p>to</p>
<p>header</p>
<p>one</p>
<h1 id="header-one-target">Header One</h1>
<div class="content-vh100"></div>
</div>
</div>
<div id="element-B">
<div class="content">
<p>to</p>
<p>animate</p>
<p>following</p>
<p>content</p>
<h1 id="animate-hd-b">Animate This Header</h1>
<div class="content-vh100"></div>
</div>
</div>
答案 1 :(得分:3)
添加了一些条件,这些条件应防止不必要的动画和排队(在收听scroll
并为scrollTop
设置动画时容易发生)。它会跟踪滚动方向,并且在右侧的元素已经到达其位置时不会开始动画。
var sin = $('#element-A'),
dex = $('#element-B'),
peg = sin.scrollTop();
sin.scroll(function() {
var way = sin.scrollTop(),
rate = Math.round(sin.find('h1').position().top),
area = dex.scrollTop(),
turf = Math.round(dex.find('h1').position().top),
down = way > peg;
peg = way;
// conditions for scrolling down
if (rate < 0 && down && turf) {
dex.not(':animated').animate({scrollTop: area+turf}, 700);
}
// scrolling up
if (!down && area) {
dex.not(':animated').animate({scrollTop: 0}, 700);
}
});
body {
margin: 0;
}
body > div {
width: 50%;
height: 100vh;
float: left;
overflow: auto;
}
#element-A {
background: orange;
}
#element-B {
background: yellow;
}
.content {
padding-bottom: 100vh;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="element-A">
<div class="content">
<p>content</p>
<p>content</p>
<p>content</p>
<p>content</p>
<h1 id="header-one-target">Header One</h1>
</div>
</div>
<div id="element-B">
<div class="content">
<p>content</p>
<p>content</p>
<p>content</p>
<p>content</p>
<h1 id="animate-hd-b">Animate This Header</h1>
</div>
</div>
如果元素在目标环境中的位置不同,则使用position()
比offset()
更直接,因为后者是相对于文档的。前者(在此使用)是相对于其自身的父元素的,并且应独立于其位置工作。