0

I've been unsuccessful in trying out the answers in related questions so any help would be much appreciated.

I have a modal which displays a form in an iframe - this is scrollable. The issue occurs on ios where the body scrolls underneath instead of the iframe. I need to prevent the body from scrolling and allow the iframe to scroll.

The suggested fix from dementic doesn't work properly as the body underneath the modal still scrolls unless you touch scroll the modal in exactly the right place but this is very temperamental.

Modal:

 <div class="modal fade" id="myModal">
        <div class="modal-dialog">
            <div class="modal-content bmd-modalContent">
                <div class="modal-body">
                    <div class="close-button">
                        <button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
                    </div>
                    <div class="embed-responsive embed-responsive-16by9">
                        <iframe id="formIframe" class="embed-responsive-item" frameborder="0"></iframe>
                    </div>
                </div>
            </div><!-- /.modal-content -->
        </div><!-- /.modal-dialog -->
</div><!-- /.modal -->

jQuery/js:

    (function($) {
        $.fn.bmdIframe = function( options ) {
            var self = this;
            var settings = $.extend({
                classBtn: '.bmd-modalButton',
                defaultH: 360
            }, options );      
        $(settings.classBtn).on('click', function(e) {
            var allowFullscreen = $(this).attr('data-bmdVideoFullscreen') || false;
            var url      = window.location.href;
            var fieldId = "Form_Source_URL";
            var trackingURL = $(this).attr("data-bmdSrc") + '?' + fieldId + '=' + url;

            var dataVideo = {
                'src': trackingURL,
                'height': $(this).attr('data-bmdHeight') || settings.defaultH,
                'width': $(this).attr('data-bmdWidth') || settings.defaultW
            };

            if ( allowFullscreen ) dataVideo.allowfullscreen = "";


            $(self).find("iframe").attr(dataVideo);


        });


        this.on('hidden.bs.modal', function(){
            $(this).find('iframe').html("").attr("src", "");
        });

        return this;
    };

})(jQuery);

jQuery(document).ready(function(){
    jQuery("#myModal").bmdIframe();

});

//attempted fix to stop body scrolling
var iframe = document.getElementById('formIframe');
iframe.addEventListener('touchmove', function(e) {
    e.preventDefault();
}, false);
  • 1
    Create a class that prevents scroll on the body `.no-scroll { overflow:hidden }` and attach/remove it when the modal opens/closes – Rafael Herscovici Feb 20 '19 at 10:33
  • Possible duplicate of [Prevent BODY from scrolling when a modal is opened](https://stackoverflow.com/questions/9538868/prevent-body-from-scrolling-when-a-modal-is-opened) – Rafael Herscovici Feb 20 '19 at 10:34
  • @Dementic this doesn't completely work. The body behind the modal still moves unless you touch scroll in one exact place. Is there any way to improve this as it will frustrate users? Thanks. – aestheticare Feb 20 '19 at 11:17
  • @aestheticare is correct. this is not enough. will soon post solution I am using – allenski Apr 09 '19 at 20:07

1 Answers1

0

In project I used this was for Semantic UI modals, and even reused same functionality to help with a custom Coveo modal/popup.

Here is the reusable JQuery function:

// Definite way of removing body scrollbar (mainly for iOS).
forceRemoveBodyScrollbar = function(removeScrollbar) {
    bodyScrollPositionBeforeScrollbarRemoved;

    if (removeScrollbar) {
        bodyScrollPositionBeforeScrollbarRemoved = $(window).scrollTop();

        // Add body class that prevents scrolling behind pop up.
        $('body').addClass('force-remove-body-scrollbar').css('top', '-' + bodyScrollPositionBeforeScrollbarRemoved + 'px');
    } else {
        // Remove attributes used to prevent scrolling of content behind Coveo pop up.
        $('body').removeClass('force-remove-body-scrollbar').removeAttr('style');

        // Scroll back to original top position prior to clicking Filters button.
        $(window).scrollTop(bodyScrollPositionBeforeScrollbarRemoved);
    }
}

CSS to help with the class that is added/removed:

body.force-remove-body-scrollbar {
    position: fixed;
    top: 0;
    right: 0;
    bottom: 0;
    left: 0;
    width: 100%;
    height: auto;
    transition: none;
}

Now, where ever you are executing code to OPEN modal just add forceRemoveBodyScrollbar(true);

Example: if modal opens on click of a button:

$('.myOpenModalButton').on('click', function() {
    forceRemoveBodyScrollbar(true);

    // Other Modal related JS.
}

And where ever you are executing code to CLOSE modal just add forceRemoveBodyScrollbar(false);

Example: can bind to click event of close button and dark background that appears behind the modal like so:

$('.modalCloseButton, .modalDarkBackground').bind('click', function() {
    forceRemoveBodyScrollbar(false);
});
allenski
  • 1,652
  • 4
  • 23
  • 39