Как прокручивать страницу, когда модальный диалог длиннее экрана?

87

В моем приложении есть модальный диалог, который может быть довольно длинным в направлении y. Это создает проблему, при которой часть содержимого диалогового окна скрывается в нижней части страницы.

введите описание изображения здесь

Я хотел бы, чтобы полоса прокрутки окна прокручивала диалоговое окно, когда оно отображается, и слишком длинное, чтобы поместиться на экране, но оставляла основное тело на месте за модальным окном. Если вы используете Trello, тогда вы знаете, к чему я стремлюсь.

Возможно ли это без использования JavaScript для управления полосой прокрутки?

Вот CSS, который я применил к модальному окну и диалогу:

body.blocked {
  overflow: hidden;
}

.modal-screen {
  background: #717174;
  position: fixed;
  overflow: hidden;
  width: 100%;
  height: 100%;
  top: 0;
  left: 0;
  opacity: 0.9;
  z-index: 50;
}

.dialog {
  background: #fff;
  position: fixed;
  padding: 12px;
  top: 20%;
  left: 50%;
  z-index: 10000;
  border-radius: 5px;
  box-shadow: 0, 0, 8px, #111;
}
Дэвид Туйт
источник
попробуйте overflow: auto или overflow: scroll в диалоге ...
lakshmi priya

Ответы:

198

просто используйте

.modal-body {
    max-height: calc(100vh - 210px);
    overflow-y: auto;
}

он упорядочит ваше модальное окно, а затем даст ему вертикальную прокрутку

Амит Кумар Павар
источник
7
Это должен быть принятый ответ. Элегантно и просто.
brianfit
2
почему мы должны использовать 210 пикселей? Есть ли какая-то особая причина?
ShellZero
9
@ShellZero, это сумма: модального заголовка, модального нижнего колонтитула, верхнего и нижнего пробелов между модальными границами и границами окна.
Сталинко 01
3
Есть ли решение без жесткого кодирования нижнего колонтитула и высоты заголовка?
Павел
2
Если вы хотите, чтобы на iOS он выглядел как обычная прокрутка, вам нужно добавить -webkit-overflow-scrolling: touch; также, потому что Mobile Safari обрабатывает прокрутку переполнения иначе, чем обычную прокрутку страницы, если специально не указано иное.
Адам Гертель
40

Вот что исправило для меня:

max-height: 100%;
overflow-y: auto;

РЕДАКТИРОВАТЬ : теперь я использую тот же метод, который в настоящее время используется в Twitter, где модальное окно действует как отдельная страница поверх текущего содержимого, а содержимое за модальным окном не перемещается при прокрутке.

По сути это так:

var scrollBarWidth = window.innerWidth - document.body.offsetWidth;
$('body').css({
  marginRight: scrollBarWidth,
  overflow: 'hidden'
});
$modal.show();

С помощью этого CSS в модальном окне:

position: fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
overflow: auto;

JSFiddle: https://jsfiddle.net/0x0049/koodkcng/
Чистая версия JS (IE9 +): https://jsfiddle.net/0x0049/koodkcng/1/

Это работает независимо от высоты или ширины страницы или модального диалога, позволяет прокручивать независимо от того, где находится ваша мышь / палец, не имеет резкого скачка, который есть в некоторых решениях, которые отключают прокрутку для основного содержимого, и отлично выглядит.

0x0049
источник
Это единственный ответ, который касается OP. Как прокручивать СТРАНИЦУ, когда модальное окно слишком длинное. на самом деле он не прокручивает страницу, но создает иллюзию прокрутки страницы, что соответствует варианту использования, когда не требуется занимать вертикальное пространство с нижним полем на экране. все другие решения, включая принятый ответ, имеют эту проблему.
Ynot
13

+ Изменить position

position:fixed;
overflow: hidden;

к

position:absolute;
overflow:scroll;
bitoshi.n
источник
1
Боюсь, не работает. Как будто окно не понимает, что диалог имеет высоту.
Дэвид Туйт
Проблема в том, может position: fixed;ли это стать абсолютным или иначе?
bitoshi.n
2
Если я это сделаю, то столкнусь с другой проблемой. Если пользователь уже прокручивается вниз по странице, когда открывает диалоговое окно, он появится в самом верху страницы, вне кадра текущего окна.
Дэвид Туйт
1
Это сработало для меня - как в обычных модальных окнах, так и когда у меня было модальное окно в модальном (который Bootstrap говорит, что перекрывающиеся модальные окна не поддерживаются ... для этого требуется специальный код ).
eggy 02
На самом деле это правильный ответ на OP, потому что вы прокручиваете страницу, а не прокручиваете модальное
окно
6

Вот моя демонстрация модального окна, которое автоматически меняет размер в соответствии с его содержимым и начинает прокрутку, когда оно не помещается в окно.

Демонстрация модального окна (см. Комментарии в исходном коде HTML)

Все сделано только с помощью HTML и CSS - JS не требуется для отображения и изменения размера модального окна (но, конечно, он вам все равно нужен для отображения окна - в новой версии JS совсем не нужен).

Обновление (больше демонстраций):

Дело в том, чтобы иметь внешний и внутренний DIV, где внешний определяет фиксированное положение, а внутренний создает прокрутку. (В демонстрации на самом деле больше DIV, чтобы они выглядели как реальное модальное окно.)

        #modal {
            position: fixed;
            transform: translate(0,0);
            width: auto; left: 0; right: 0;
            height: auto; top: 0; bottom: 0;
            z-index: 990; /* display above everything else */
            padding: 20px; /* create padding for inner window - page under modal window will be still visible */
        }

        #modal .outer {
            box-sizing: border-box; -moz-box-sizing: border-box; -webkit-box-sizing: border-box; -o-box-sizing: border-box;
            width: 100%;
            height: 100%;
            position: relative;
            z-index: 999;
        }

        #modal .inner {
            box-sizing: border-box; -moz-box-sizing: border-box; -webkit-box-sizing: border-box; -o-box-sizing: border-box;
            width: 100%;
            height: auto;       /* allow to fit content (if smaller)... */
            max-height: 100%;   /* ... but make sure it does not overflow browser window */

            /* allow vertical scrolling if required */
            overflow-x: hidden;
            overflow-y: auto;

            /* definition of modal window layout */
            background: #ffffff;
            border: 2px solid #222222;
            border-radius: 16px; /* some nice (modern) round corners */
            padding: 16px;       /* make sure inner elements does not overflow round corners */
        }
Радек Печ
источник
Можно ли заблокировать страницу при открытии всплывающего окна, чтобы предотвратить прокрутку? Если у пользователя есть мышь за пределами всплывающего окна, он будет прокручивать страницу вместо всплывающего окна, и как только это произойдет, и он переместится во всплывающее окно, он получит всплывающее окно и прокрутку страницы. Спасибо
Adyyda
@Adyyda Вы можете остановить прокрутку, заключив страницу в DIV с помощью overflow:hiddenи установив ее размер, равный размеру страницы, а ее размер margin-top- отрицательный scroll-top.
Радек Печ
Это было хорошее и подходящее решение, Радек - отзывчивый, кроссбраузерный, просто сделанный с использованием CSS.
Сэкономили
@RadekPech, чем это отличается от нынешнего html,body{ overflow:hidden }?
Стивен Вашон,
@StevenVachon На такой простой странице, как демонстрационная версия, и ограниченном количестве поддерживаемых браузеров может не быть никакой разницы. Но на более сложной странице или в конкретном браузере настройки html,body{ overflow:hidden }могут работать не так, как ожидалось. Так что это может показаться излишним, но лучше перестраховаться .
Радек Печ
2

Одно только фиксированное позиционирование должно было решить эту проблему, но еще один хороший способ избежать этой проблемы - разместить модальные блоки div или элементы внизу страницы, а не в макете вашего сайта. Большинство модальных плагинов предоставляют свое модальное позиционирование абсолютное, чтобы пользователь мог продолжать прокрутку главной страницы.

<html>
        <body>
        <!-- Put all your page layouts and elements


        <!-- Let the last element be the modal elemment  -->
        <div id="myModals">
        ...
        </div>

        </body>
</html>
Чимди2000
источник
2

Вот .. У меня отлично работает

.modal-body { 
    max-height:500px; 
    overflow-y:auto;
}
Эванс Квачи
источник
2

простой способ сделать это, добавив этот CSS Итак, вы только что добавили это в CSS:

.modal-body {
position: relative;
padding: 20px;
height: 200px;
overflow-y: scroll;
}

и он работает!

Ашикур Рахман
источник
1

position:fixedподразумевает, что модальное окно останется фиксированным относительно точки обзора. Я согласен с вашей оценкой, что это уместно в этом сценарии, помня об этом, почему вы не добавляете полосу прокрутки в само модальное окно?

Если это так, то правильные max-heightи overflowсвойства должны помочь.

ов
источник
0

В конце концов, мне пришлось внести изменения в содержимое страницы за модальным экраном, чтобы гарантировать, что оно никогда не будет достаточно длинным для прокрутки страницы.

Как только я это сделал, проблемы, с которыми я столкнулся при обращении position: absoluteк диалоговому окну, были решены, поскольку пользователь больше не мог прокручивать страницу вниз.

Дэвид Туйт
источник
Вы только что пропустили свой выпуск
Амит Кумар Павар
как вопрос, так и ответ на ваше сообщение, и вы также принимаете свой ответ, тогда почему вы публикуете здесь вопрос?
Thiyagu
2
@Thiyagu, что считается нормальным. Если спрашивающий находит решение, он сам должен опубликовать ответ. Они также могут принять любой ответ, который им помог. Конечная цель - помочь сообществу в целом.
Ошибки
0

Панель прокрутки страницы окна кликабельна, когда открыто модальное окно

Этот мне подходит. Чистый CSS.

<style type="text/css">

body.modal-open {
padding-right: 17px !important;
}

.modal-backdrop.in {
margin-right: 16px; 

</style>

Попробуй и дай мне знать

Хируюки Ксанада
источник
-1

Я хотел добавить свой чистый CSS ответ на эту проблему модальных окон с динамической шириной и высотой. Следующий код также работает со следующими требованиями:

  1. Поместите модальное окно в центр экрана
  2. Если модальное окно выше, чем область просмотра, затемнение прокрутки (не модальное содержимое)

HTML:

<div class="modal">
    <div class="modal__content">
        (Long) Content
    </div>
</div>

CSS / МЕНЬШЕ:

.modal {
    position: fixed;
    display: flex;
    align-items: center;
    top: 0;
    left: 0;
    right: 0;
    bottom: 0;
    padding: @qquad;
    overflow-y: auto;
    background: rgba(0, 0, 0, 0.7);
    z-index: @zindex-modal;

    &__content {
        width: 900px;
        margin: auto;
        max-width: 90%;
        padding: @quad;
        background: white;
        box-shadow: 0 0 5px 0 rgba(0, 0, 0, 0.75);
    }
}

Таким образом, модальное окно всегда находится в области просмотра. Ширина и высота модального окна произвольны. Для простоты я удалил из него значок закрытия.

Karlludwigweise
источник