Я столкнулся со странной проблемой при попытке разместить всплывающее окно position: absolute в моем проекте.
Что касается position: absolute, MDN говорит:
The element is removed from the normal document flow, and no space is created for the element in the page layout.
К сожалению, в приведенном ниже примере размещение элемента с помощью right: 0 и transform: translateX(100%) создает дополнительное пространство за пределами тела, как если бы элемент должен был быть position: relative. Этого не произойдет, если мы будем использовать left: 0 и transform: translateX(-100%).
.parent {
width: 100%;
height: 100vh;
border: 1px solid red;
background-color: magenta;
}
.child {
position: absolute;
transform: translateX(100%);
width: 100px;
height: 50%;
border: 1px solid black;
right: 0;
background-color: yellow;
} <div class = "parent">
<div class = "child"></div>
</div>Вот ссылка на пример проблемы https://jsbin.com/fikonusayi/edit?html,css,output
Это ошибка браузера или (не) ожидаемая функция?
P.S. Обнаружен в Chrome и Safari.
Пожалуйста, добавьте свой минимальный воспроизводимый пример к самому вопросу; ссылка на JSFiddle не соответствует правилам.
PS можете найти свой ответ здесь
@TemaniAfif Ваш комментарий бесполезен.
@TylerH Спасибо за источник. Обновил пост. Также интересно прочитать о матрице преобразования. Тем не менее, меня все еще путают две вещи: 1) почему того же эффекта можно достичь, удалив transform и добавив right: 100000px, и 2) почему этого эффекта нет у position: fixed? Не могли бы вы уточнить?
@TylerH как он отвечает на вопрос? преобразование добавляется к абсолютному элементу, а не к родительскому элементу .. здесь речь идет о переполнении, не содержащем блока
@saranc он действительно создает дополнительное пространство в процентах ниже 100%, я пробовал его на 25/50/75 и 90% ..






Проблема здесь в overflow, а не в документообороте. Если мы обратимся к спецификация:
Generally, the content of a block box is confined to the content edges of the box. In certain cases, a box may overflow, meaning its content lies partly or entirely outside of the box, e.g.:
...
A descendant box is positioned absolutely, partly outside the box. Such boxes are not always clipped by the overflow property on their ancestors; specifically, they are not clipped by the overflow of any ancestor between themselves and their containing block
....
Вы можете заметить, что нет другого позиционированного элемента, кроме child, поэтому содержащий блокchild будет окном просмотра. И уловка здесь в том, что полоса прокрутки всегда добавляется к содержащему блоку, начиная слева (горизонтальная прокрутка) или сверху (вертикальная прокрутка), поэтому любое переполнение сверху или слева станет недоступным.
Вот иллюстрация, чтобы лучше понять проблему:
.parent {
width: 100%;
height: 100vh;
border: 1px solid red;
background-color: magenta;
box-sizing:border-box;
}
.child {
position: absolute;
width: 100px;
height: 50%;
border: 1px solid black;
left: 0;
background-color: yellow;
animation:move 3s infinite linear alternate;
}
@keyframes move{
from {left:-100px}
to {left:100%}
}
body {
margin:0;
}<div class = "parent">
<div class = "child"></div>
</div>Как видите, прокрутка есть только при переполнении элемента слева. Та же логика, если рассматривать верх / низ
.parent {
width: 100%;
height: 100vh;
border: 1px solid red;
background-color: magenta;
box-sizing:border-box;
}
.child {
position: absolute;
width: 100px;
height: 50%;
border: 1px solid black;
left: 0;
background-color: yellow;
animation:move 3s infinite linear alternate;
}
@keyframes move{
from {top:-100px}
to {top:100%}
}
body {
margin:0;
}<div class = "parent">
<div class = "child"></div>
</div>И чтобы подтвердить, что ваш элемент действительно удален из потока, просто добавьте контент и удалите фиксированную высоту из родительского элемента, и вы увидите, что для вашего элемента не предусмотрено места:
.parent {
border: 1px solid red;
background-color: magenta;
position: relative;
box-sizing:border-box;
}
.child {
position: absolute;
width: 100px;
height: 50%;
border: 1px solid black;
top:0;
left: 0;
background-color: yellow;
animation:move 3s infinite linear alternate;
}
@keyframes move{
from {left:-100px;top:-100px;}
to {left:100%;top:100%;}
}
body {
margin:0;
border:2px solid red;
}<div class = "parent">
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Cras eget maximus nibh. Nam non libero molestie, placerat lorem sed, congue arcu. Aliquam eu ultrices nisi, sed facilisis purus. Suspendisse sit amet tincidunt massa, varius tempor mi. Suspendisse semper finibus ipsum in varius. Maecenas id commodo mi, vitae molestie diam. Nulla a risus cursus, auctor ligula sit amet, vestibulum purus. In in turpis non mi auctor viverra porta ac magna.
<div class = "child"></div>
</div>В отличие от position:relative:
.parent {
border: 1px solid red;
background-color: magenta;
position: relative;
box-sizing:border-box;
}
.child {
position: relative;
width: 100px;
height: 50px;
border: 1px solid black;
top:0;
left: 0;
background-color: yellow;
animation:move 3s infinite linear alternate;
}
@keyframes move{
from {left:-100px;top:-100px;}
to {left:100%;top:100px;}
}
body {
margin:0;
border:2px solid red;
}<div class = "parent">
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Cras eget maximus nibh. Nam non libero molestie, placerat lorem sed, congue arcu. Aliquam eu ultrices nisi, sed facilisis purus. Suspendisse sit amet tincidunt massa, varius tempor mi. Suspendisse semper finibus ipsum in varius. Maecenas id commodo mi, vitae molestie diam. Nulla a risus cursus, auctor ligula sit amet, vestibulum purus. In in turpis non mi auctor viverra porta ac magna.
<div class = "child"></div>
</div>Почему этого не происходит с position:fixed? просто потому, что в спецификация ничего не указано. Вот все случаи переполнения:
- A line cannot be broken, causing the line box to be wider than the block box.
- A block-level box is too wide for the containing block. This may happen when an element's 'width' property has a value that causes the generated block box to spill over sides of the containing block.
- An element's height exceeds an explicit height assigned to the containing block (i.e., the containing block's height is determined by the 'height' property, not by content height).
- A descendant box is positioned absolutely, partly outside the box. Such boxes are not always clipped by the overflow property on their ancestors; specifically, they are not clipped by the overflow of any ancestor between themselves and their containing block
- A descendant box has negative margins, causing it to be positioned partly outside the box. The 'text-indent' property causes an inline box to hang off either the left or right edge of the block box.
Большой! Я программирую 3 года и практически никогда не обращал внимания на переполнение. Этот случай был для меня в новинку. Какие-либо архитектурные / семантические решения, которые вы бы посоветовали избежать / исправить переполнение?
@RolandJegorov Я не думаю, что переполнение - это проблема для начала ... в большинстве случаев это намеренно, особенно для какой-то анимации, где мы скрываем элементы и заставляем их появляться (используется с переполнением: скрыто, чтобы избежать прокрутки) . Но в случае, если это случайно, вам просто нужно обратить внимание, нет общих правил, но старайтесь избегать фиксированной высоты, не забывайте box-sizing:border-box при работе с заполнением / границей / шириной или высотой. с position: absolute / fixed убедитесь, что правильно установили положение и т. д.
Чтобы добавить, это происходит справа, а не слева, потому что мы используем систему слева направо, сверху вниз. Естественно, вещи могут перетекать только вправо или вниз.