[javascript] 일시적으로 스크롤을 비활성화하는 방법은 무엇입니까?

scrollTo jQuery 플러그인을 사용하고 있으며 Javascript를 통해 window 요소에서 일시적으로 스크롤을 비활성화 할 수 있는지 알고 싶습니다. 스크롤을 사용하지 않으려는 이유는 scrollTo가 애니메이션을 적용하는 동안 스크롤 할 때 실제로 추악하기 때문입니다.)

물론 $("body").css("overflow", "hidden");애니메이션을 멈출 때 a를 수행 한 다음 자동으로 되돌릴 수 있지만 스크롤 막대가 여전히 보이지만 비활성화되어 있으면 더 좋습니다.



답변

scroll이벤트는 취소 할 수 없습니다. 그러나 다음 상호 작용 이벤트 를 취소 하여 이를 수행 할 수 있습니다.
마우스 터치 스크롤단추 관련된 과 .

[ 실무 데모 ]

// left: 37, up: 38, right: 39, down: 40,
// spacebar: 32, pageup: 33, pagedown: 34, end: 35, home: 36
var keys = {37: 1, 38: 1, 39: 1, 40: 1};

function preventDefault(e) {
  e.preventDefault();
}

function preventDefaultForScrollKeys(e) {
  if (keys[e.keyCode]) {
    preventDefault(e);
    return false;
  }
}

// modern Chrome requires { passive: false } when adding event
var supportsPassive = false;
try {
  window.addEventListener("test", null, Object.defineProperty({}, 'passive', {
    get: function () { supportsPassive = true; }
  }));
} catch(e) {}

var wheelOpt = supportsPassive ? { passive: false } : false;
var wheelEvent = 'onwheel' in document.createElement('div') ? 'wheel' : 'mousewheel';

// call this to Disable
function disableScroll() {
  window.addEventListener('DOMMouseScroll', preventDefault, false); // older FF
  window.addEventListener(wheelEvent, preventDefault, wheelOpt); // modern desktop
  window.addEventListener('touchmove', preventDefault, wheelOpt); // mobile
  window.addEventListener('keydown', preventDefaultForScrollKeys, false);
}

// call this to Enable
function enableScroll() {
  window.removeEventListener('DOMMouseScroll', preventDefault, false);
  window.removeEventListener(wheelEvent, preventDefault, wheelOpt);
  window.removeEventListener('touchmove', preventDefault, wheelOpt);
  window.removeEventListener('keydown', preventDefaultForScrollKeys, false);
}

업데이트 : 패시브 리스너가있는 고정 Chrome 데스크톱 및 최신 모바일 브라우저


답변

본문에 클래스를 추가하여 간단하게 수행하십시오.

.stop-scrolling {
  height: 100%;
  overflow: hidden;
}

클래스를 추가 한 다음 IE, FF, Safari 및 Chrome에서 테스트 한 스크롤을 다시 활성화하려는 경우 제거하십시오.

$('body').addClass('stop-scrolling')

내용은 모바일 장치 , 당신은 처리해야합니다 touchmove이벤트를 :

$('body').bind('touchmove', function(e){e.preventDefault()})

스크롤을 다시 활성화하려면 바인딩을 해제하십시오. iOS6 및 Android 2.3.3에서 테스트

$('body').unbind('touchmove')


답변

이를 수행하는 가장 기본적인 방법은 다음과 같습니다.

window.onscroll = function () { window.scrollTo(0, 0); };

IE6에서는 다소 까다 롭습니다.


답변

다음 솔루션은 기본이지만 순수한 JavaScript입니다 (jQuery 없음).

function disableScrolling(){
    var x=window.scrollX;
    var y=window.scrollY;
    window.onscroll=function(){window.scrollTo(x, y);};
}

function enableScrolling(){
    window.onscroll=function(){};
}


답변

이 솔루션은 사용자가 맨 위로 이동하는 것과 달리 스크롤이 비활성화 된 상태에서 현재 스크롤 위치를 유지합니다.

galambalaz의 답변을 기반으로 하지만 터치 장치를 지원하며 jquery 플러그인 래퍼를 사용하여 단일 객체로 리팩토링했습니다.

여기 데모.

여기 github에서.

/**
 * $.disablescroll
 * Author: Josh Harrison - aloof.co
 *
 * Disables scroll events from mousewheels, touchmoves and keypresses.
 * Use while jQuery is animating the scroll position for a guaranteed super-smooth ride!
 */

;(function($) {

    "use strict";

    var instance, proto;

    function UserScrollDisabler($container, options) {
        // spacebar: 32, pageup: 33, pagedown: 34, end: 35, home: 36
        // left: 37, up: 38, right: 39, down: 40
        this.opts = $.extend({
            handleKeys : true,
            scrollEventKeys : [32, 33, 34, 35, 36, 37, 38, 39, 40]
        }, options);

        this.$container = $container;
        this.$document = $(document);
        this.lockToScrollPos = [0, 0];

        this.disable();
    }

    proto = UserScrollDisabler.prototype;

    proto.disable = function() {
        var t = this;

        t.lockToScrollPos = [
            t.$container.scrollLeft(),
            t.$container.scrollTop()
        ];

        t.$container.on(
            "mousewheel.disablescroll DOMMouseScroll.disablescroll touchmove.disablescroll",
            t._handleWheel
        );

        t.$container.on("scroll.disablescroll", function() {
            t._handleScrollbar.call(t);
        });

        if(t.opts.handleKeys) {
            t.$document.on("keydown.disablescroll", function(event) {
                t._handleKeydown.call(t, event);
            });
        }
    };

    proto.undo = function() {
        var t = this;
        t.$container.off(".disablescroll");
        if(t.opts.handleKeys) {
            t.$document.off(".disablescroll");
        }
    };

    proto._handleWheel = function(event) {
        event.preventDefault();
    };

    proto._handleScrollbar = function() {
        this.$container.scrollLeft(this.lockToScrollPos[0]);
        this.$container.scrollTop(this.lockToScrollPos[1]);
    };

    proto._handleKeydown = function(event) {
        for (var i = 0; i < this.opts.scrollEventKeys.length; i++) {
            if (event.keyCode === this.opts.scrollEventKeys[i]) {
                event.preventDefault();
                return;
            }
        }
    };


    // Plugin wrapper for object
    $.fn.disablescroll = function(method) {

        // If calling for the first time, instantiate the object and save
        // reference. The plugin can therefore only be instantiated once per
        // page. You can pass options object in through the method parameter.
        if( ! instance && (typeof method === "object" || ! method)) {
            instance = new UserScrollDisabler(this, method);
        }

        // Instance already created, and a method is being explicitly called,
        // e.g. .disablescroll('undo');
        else if(instance && instance[method]) {
            instance[method].call(instance);
        }

    };

    // Global access
    window.UserScrollDisabler = UserScrollDisabler;

})(jQuery);


답변

오래된 게시물에 답변을해서 죄송하지만 해결책을 찾고 있었고이 질문을 발견했습니다.

컨테이너에 높이를 100 %로 설정하고 스크롤 막대를 표시하는 등이 문제에 대한 해결 방법이 많이 있습니다. overflow-y: scroll 지정 스타일을 지정 있습니다.

내 경우에는 방금 스크롤 막대 overflow: hidden를 사용하여 본문에 추가 하는 동안 표시되는 div를 만들었습니다 .

function disableScroll() {
    document.getElementById('scrollbar').style.display = 'block';
    document.body.style.overflow = 'hidden';
}

요소 스크롤 막대는 다음 스타일을 가져야합니다.

overflow-y: scroll; top: 0; right: 0; display: none; height: 100%; position: fixed;

이것은 회색 스크롤 막대를 보여줍니다. 향후 방문자에게 도움이되기를 바랍니다.


답변

나는이 문제에 대한 해결책을 찾고 있었지만 위의 해결책 중 어느 것에도 만족하지 않았기 때문에 ( 이 대답을 쓰는 현재 ) 해결책을 찾았 습니다.

CSS

.scrollDisabled {
    position: fixed;
    margin-top: 0;// override by JS to use acc to curr $(window).scrollTop()
    width: 100%;
}

JS

var y_offsetWhenScrollDisabled=0;

function disableScrollOnBody(){
    y_offsetWhenScrollDisabled= $(window).scrollTop();
    $('body').addClass('scrollDisabled').css('margin-top', -y_offsetWhenScrollDisabled);
}
function enableScrollOnBody(){
    $('body').removeClass('scrollDisabled').css('margin-top', 0);
    $(window).scrollTop(y_offsetWhenScrollDisabled);
}