jQuery滚动到元素

我有这个input元素:

  

然后我有一些其他元素,如其他文本输入,textareas等。

当用户使用#subject单击该input时,页面应滚动到页面的最后一个元素并带有一个漂亮的动画。 它应该是一个滚动到底部而不是顶部。

页面的最后一项是带#submitsubmit按钮:

  

动画不应该太快,应该是流畅的。

我正在运行最新的jQuery版本。 我更喜欢不安装任何插件,而是使用默认的jQueryfunction来实现这一点。

假设您有一个带有id button ,请尝试以下示例:

 $("#button").click(function() { $([document.documentElement, document.body]).animate({ scrollTop: $("#elementtoScrollToID").offset().top }, 2000); }); 

我从文章Smoothly滚动到没有jQuery插件的元素的代码。 我在下面的例子中对它进行了测试。

    
Test

Test 2

jQuery .scrollTo()方法

jQuery .scrollTo(): View – Demo,API,Source

我编写了这个轻量级插件,使页面/元素滚动更加容易。 您可以灵活地传入目标元素或指定值。 也许这可能是jQuery下一次正式发布的一部分,你怎么看?


示例用法:

 $('body').scrollTo('#target'); // Scroll screen to target element $('body').scrollTo(500); // Scroll screen 500 pixels down $('#scrollable').scrollTo(100); // Scroll individual element 100 pixels down 

选项:

scrollTarget :表示所需滚动位置的元素,字符串或数字。

offsetTop :一个数字,用于定义滚动目标上方的附加间距。

duration :确定动画运行时间的字符串或数字。

easing :一个字符串,指示要用于转换的缓动函数。

complete :动画完成后调用的函数。

如果你对平滑滚动效果不太感兴趣并且只想滚动到特定元素,那么你不需要一些jQuery函数。 Javascript已涵盖您的案例:

https://developer.mozilla.org/en-US/docs/Web/API/element.scrollIntoView

所以你需要做的就是: $("selector").get(0).scrollIntoView();

.get(0)是因为我们想要检索JavaScript的DOM元素而不是JQuery的DOM元素。

查看ScrollTo插件。 你可以在这里看到演示。

我希望它有所帮助。

使用这个简单的脚本

 if($(window.location.hash).length > 0){ $('html, body').animate({ scrollTop: $(window.location.hash).offset().top}, 1000); } 

如果在url中找到了一个hash标签,那么scrollTo会动画到ID。 如果未找到哈希标记,则忽略该脚本。

 jQuery(document).ready(function($) { $('a[href^="#"]').bind('click.smoothscroll',function (e) { e.preventDefault(); var target = this.hash, $target = $(target); $('html, body').stop().animate( { 'scrollTop': $target.offset().top-40 }, 900, 'swing', function () { window.location.hash = target; } ); } ); } ); 
   

史蒂夫和彼得的解决方案非常有效。

但在某些情况下,您可能必须将值转换为整数。 奇怪的是, $("...").offset().top的返回值有时是float
使用: parseInt($("....").offset().top)

例如:

 $("#button").click(function() { $('html, body').animate({ scrollTop: parseInt($("#elementtoScrollToID").offset().top) }, 2000); }); 

紧凑版“动画”解决方案。

 $.fn.scrollTo = function (speed) { if (typeof(speed) === 'undefined') speed = 1000; $('html, body').animate({ scrollTop: parseInt($(this).offset().top) }, speed); }; 

基本用法: $('#your_element').scrollTo();

如果您只处理滚动到输入元素,则可以使用focus() 。 例如,如果要滚动到第一个可见输入:

 $(':input:visible').first().focus(); 

或者带有.error类的容器中的第一个可见输入:

 $('.error :input:visible').first().focus(); 

感谢Tricia Ball指出这一点!

使用此解决方案,您不需要任何插件,除了在结束标记之前放置脚本之外,不需要任何设置

 $("a[href^='#']").on("click", function(e) { e.preventDefault(); $("html, body").animate({ scrollTop: $($(this).attr("href")).offset().top }, 1000); }); if ($(window.location.hash).length > 1) { $("html, body").animate({ scrollTop: $(window.location.hash).offset().top }, 1000); } 

在加载时,如果地址中有哈希,我们滚动到它。

而且 – 每当你点击一个带有href哈希a链接时,例如#top ,我们就滚动到它。

在大多数情况下,最好使用插件。 认真。 我要在这里兜售我的 。 当然还有其他人。 但请检查他们是否真的避免了你想要一个插件的陷阱 – 而不是所有的插件。

我已经写过在其他地方使用插件的原因。 简而言之,这里的一个衬垫支撑了大多数答案

 $('html, body').animate( { scrollTop: $target.offset().top }, duration ); 

用户体验很糟糕。

  • 动画不响应用户操作。 即使用户点击,点击或尝试滚动,它也会继续。

  • 如果动画的起点接近目标元素,则动画非常缓慢。

  • 如果目标元素位于页面底部附近,则无法滚动到窗口顶部。 滚动动画然后在中间运动中突然停止。

要处理这些问题(以及其他一些问题 ),您可以使用我的插件jQuery.scrollable 。 然后呼叫成为

 $( window ).scrollTo( targetPosition ); 

就是这样。 当然,还有更多选择 。

关于目标位置, $target.offset().top在大多数情况下完成工作。 但请注意,返回的值不会考虑html元素的边框( 请参阅此演示 )。 如果您在任何情况下都需要目标位置准确,最好使用

 targetPosition = $( window ).scrollTop() + $target[0].getBoundingClientRect().top; 

即使设置了html元素的边框,这也有效。

这是我使用generics类选择器抽象ID和href的方法

 $(function() { // Generic selector to be used anywhere $(".js-scroll-to").click(function(e) { // Get the href dynamically var destination = $(this).attr('href'); // Prevent href=“#” link from changing the URL hash (optional) e.preventDefault(); // Animate scroll to destination $('html, body').animate({ scrollTop: $(destination).offset().top }, 500); }); }); 
   

非常简单易用的自定义jQuery插件。 只需将属性scroll=添加到可点击元素,并将其值设置为要滚动到的选择器。

像这样: Click me 。 它可以用在任何元素上。

 (function($){ $.fn.animateScroll = function(){ console.log($('[scroll]')); $('[scroll]').click(function(){ selector = $($(this).attr('scroll')); console.log(selector); console.log(selector.offset().top); $('html body').animate( {scrollTop: (selector.offset().top)}, //- $(window).scrollTop() 1000 ); }); } })(jQuery); // RUN jQuery(document).ready(function($) { $().animateScroll(); }); // IN HTML EXAMPLE // RUN ONCLICK ON OBJECT WITH ATTRIBUTE SCROLL=".SELECTOR" // Click To Scroll 
 var scrollTo = function($parent, $element) { var topDiff = $element.position().top - $parent.position().top; $parent.animate({ scrollTop : topDiff }, 100); }; 

动画:

 // slide to top of the page $('.up').click(function () { $("html, body").animate({ scrollTop: 0 }, 600); return false; }); // slide page to anchor $('.menutop b').click(function(){ //event.preventDefault(); $('html, body').animate({ scrollTop: $( $(this).attr('href') ).offset().top }, 600); return false; }); // Scroll to class, div $("#button").click(function() { $('html, body').animate({ scrollTop: $("#target-element").offset().top }, 1000); }); // div background animate $(window).scroll(function () { var x = $(this).scrollTop(); // freezze div background $('.banner0').css('background-position', '0px ' + x +'px'); // from left to right $('.banner0').css('background-position', x+'px ' +'0px'); // from right to left $('.banner0').css('background-position', -x+'px ' +'0px'); // from bottom to top $('#skills').css('background-position', '0px ' + -x + 'px'); // move background from top to bottom $('.skills1').css('background-position', '0% ' + parseInt(-x / 1) + 'px' + ', 0% ' + parseInt(-x / 1) + 'px, center top'); // Show hide mtop menu if ( x > 100 ) { $( ".menu" ).addClass( 'menushow' ); $( ".menu" ).fadeIn("slow"); $( ".menu" ).animate({opacity: 0.75}, 500); } else { $( ".menu" ).removeClass( 'menushow' ); $( ".menu" ).animate({opacity: 1}, 500); } }); // progres bar animation simple $('.bar1').each(function(i) { var width = $(this).data('width'); $(this).animate({'width' : width + '%' }, 900, function(){ // Animation complete }); }); 

$('html, body').animate(...)不适用于iphone,android chrome safari浏览器。

我必须定位页面的根内容元素。

$( ‘#cotnent’)。动画(…)

这就是我最终得到的结果

 if (navigator.userAgent.match(/(iPod|iPhone|iPad|Android)/)) { $('#content').animate({ scrollTop: $("#elementtoScrollToID").offset().top }, 'slow'); } else{ $('html, body').animate({ scrollTop: $("#elementtoScrollToID").offset().top }, 'slow'); } 

所有正文内容都与#content div相连

  ....  
....

轻松实现页面滚动到目标div id的方法

 var targetOffset = $('#divID').offset().top; $('html, body').animate({scrollTop: targetOffset}, 1000); 
 $('html, body').animate({scrollTop: Math.min( $(to).offset().top-margintop, //margintop is the margin above the target $('body')[0].scrollHeight-$('body').height()) //if the target is at the bottom }, 2000); 

要显示完整元素(如果可以使用当前窗口大小):

 var element = $("#some_element"); var elementHeight = element.height(); var windowHeight = $(window).height(); var offset = Math.min(elementHeight, windowHeight) + element.offset().top; $('html, body').animate({ scrollTop: offset }, 500); 

我编写了一个通用函数,可以滚动到jQuery对象,CSS选择器或数值。

用法示例:

 // scroll to "#target-element": $.scrollTo("#target-element"); // scroll to 80 pixels above first element with class ".invalid": $.scrollTo(".invalid", -80); // scroll a container with id "#my-container" to 300 pixels from its top: $.scrollTo(300, 0, "slow", "#my-container"); 

函数的代码:

 /** * Scrolls the container to the target position minus the offset * * @param target - the destination to scroll to, can be a jQuery object * jQuery selector, or numeric position * @param offset - the offset in pixels from the target position, eg * pass -80 to scroll to 80 pixels above the target * @param speed - the scroll speed in milliseconds, or one of the * strings "fast" or "slow". default: 500 * @param container - a jQuery object or selector for the container to * be scrolled. default: "html, body" */ jQuery.scrollTo = function (target, offset, speed, container) { if (isNaN(target)) { if (!(target instanceof jQuery)) target = $(target); target = parseInt(target.offset().top); } container = container || "html, body"; if (!(container instanceof jQuery)) container = $(container); speed = speed || 500; offset = offset || 0; container.animate({ scrollTop: target + offset }, speed); }; 

当用户使用#subject单击该输入时,页面应滚动到页面的最后一个元素并带有一个漂亮的动画。 它应该是一个滚动到底部而不是顶部。

页面的最后一项是带有#submit的提交按钮

 $('#subject').click(function() { $('#submit').focus(); $('#subject').focus(); }); 

这将首先向下滚动到#submit然后将光标恢复为单击的输入,模拟向下滚动,并适用于大多数浏览器。 它也不需要jQuery,因为它可以用纯JavaScript编写。

这种使用focusfunction的方式可以通过链接focus调用以更好的方式模仿动画。 我没有测试过这个理论,但它看起来像这样:

  
..
..
..
..

对于它的价值,这就是我如何设法为一般元素实现这种行为,这些元素可以在滚动内部进行。 在我们的例子中,我们不会滚动整个主体,而只是具有溢出的特定元素:auto; 在更大的布局内。

它会创建目标元素高度的虚假输入,然后将焦点放在其上,无论您在可滚动层次结构中有多深,浏览器都会关注其余部分。 奇迹般有效。

 var $scrollTo = $('#someId'), inputElem = $(''); $scrollTo.prepend(inputElem); inputElem.css({ position: 'absolute', width: '1px', height: $scrollTo.height() }); inputElem.focus(); inputElem.remove(); 

我设置了一个模块scroll-element npm install scroll-element 。 它的工作原理如下:

 import { scrollToElement, scrollWindowToElement } from 'scroll-element' /* scroll the window to your target element, duration and offset optional */ let targetElement = document.getElementById('my-item') scrollWindowToElement(targetElement) /* scroll the overflow container element to your target element, duration and offset optional */ let containerElement = document.getElementById('my-container') let targetElement = document.getElementById('my-item') scrollToElement(containerElement, targetElement) 

在以下SOpost的帮助下撰写:

  • 偏移顶级的一个元件,而无需-jquery的

  • scrollTop的动画,而无需-的jQuery

这是代码:

 export const scrollToElement = function(containerElement, targetElement, duration, offset) { if (duration == null) { duration = 1000 } if (offset == null) { offset = 0 } let targetOffsetTop = getElementOffset(targetElement).top let containerOffsetTop = getElementOffset(containerElement).top let scrollTarget = targetOffsetTop + ( containerElement.scrollTop - containerOffsetTop) scrollTarget += offset scroll(containerElement, scrollTarget, duration) } export const scrollWindowToElement = function(targetElement, duration, offset) { if (duration == null) { duration = 1000 } if (offset == null) { offset = 0 } let scrollTarget = getElementOffset(targetElement).top scrollTarget += offset scrollWindow(scrollTarget, duration) } function scroll(containerElement, scrollTarget, duration) { let scrollStep = scrollTarget / (duration / 15) let interval = setInterval(() => { if ( containerElement.scrollTop < scrollTarget ) { containerElement.scrollTop += scrollStep } else { clearInterval(interval) } },15) } function scrollWindow(scrollTarget, duration) { let scrollStep = scrollTarget / (duration / 15) let interval = setInterval(() => { if ( window.scrollY < scrollTarget ) { window.scrollBy( 0, scrollStep ) } else { clearInterval(interval) } },15) } function getElementOffset(element) { let de = document.documentElement let box = element.getBoundingClientRect() let top = box.top + window.pageYOffset - de.clientTop let left = box.left + window.pageXOffset - de.clientLeft return { top: top, left: left } } 

如果你想在溢出容器中滚动(而不是上面回答的$('html, body') ),同时使用绝对定位,这是可行的方法:

 var elem = $('#myElement'), container = $('#myScrollableContainer'), pos = elem.position().top + container.scrollTop() - container.position().top; container.animate({ scrollTop: pos } 

这是Atharva的回答: https : //developer.mozilla.org/en-US/docs/Web/API/element.scrollIntoView 。 只想添加文档是否在iframe中,您可以选择父框架中的元素滚动到视图中:

  $('#element-in-parent-frame', window.parent.document).get(0).scrollIntoView();