我有一个用 CSS FlexBox 完成的列表。我已经根据一些标准 order
分配给所有 flexbox items,所以列表是视觉排序的。我还有一个按钮可以切换 flexbox container 的 flex-direction
,所以我可以恢复显示顺序。我的空间有限,所以使用 overflow-y: scroll;
并且当我使用 flex-direction
恢复列表的视觉顺序时,带有 order 的元素: 1
正在滚动到视口(viewport)中。所以当它在顶部时 (flex-direction: column;
) - 在容器的开头滚动(列表中有 10 个元素),
但是当我应用 flex-direction: column-reverse;
- 我仍然可以看到这个元素,但现在滚动在容器的底部:
为什么滚动会跟随具有最低 order
属性的元素?
这是我在 Relative codepen 中的代码或内联在下面
HTML
<div class="alternator">
<button>Reverse order</button>
</div>
<div class="wrapper">
<div class="item a10">10 away</div>
<div class="item a2">2 upon</div>
<div class="item a3">3 a</div>
<div class="item a4">4 time</div>
<div class="item a5">5 in</div>
<div class="item a6">6 a</div>
<div class="item a7">7 galaxy</div>
<div class="item a1">1 once</div>
<div class="item a8">8 very</div>
<div class="item a9">9 far</div>
</div>
CSS
.wrapper {
display: flex;
flex-direction: column;
overflow-y: scroll;
max-height: 350px;
border: 2px solid green;
width: 150px;
}
.wrapper.reversed {
flex-direction: column-reverse;
}
.item {
height: 30px;
padding: 20px;
}
.a1{order: 1;}
.a2{order: 2;}
.a3{order: 3;}
.a4{order: 4;}
.a5{order: 5;}
.a6{order: 6;}
.a7{order: 7;}
.a8{order: 8;}
.a9{order: 9;}
.a10{order: 10;}
button {
margin-bottom: 20px;
width: 150px;
height: 30px;
}
JS
const btn = document.querySelector('.alternator button');
const list = document.querySelector('.wrapper');
btn.addEventListener('click', () => {
list.classList.toggle('reversed');
})
更新 由于下面的回答涉及滚动方面,我必须在此处添加 flex-direction: *-reverse
的工作方式类似于 order
属性 -即仅在视觉上改变元素的顺序,因此 DOM 树中的第一个元素在渲染后保留在那里:
“Note: The reordering capabilities of flex layout intentionally affect only the visual rendering, leaving speech order and navigation based on the source order. This allows authors to manipulate the visual presentation while leaving the source order intact for non-CSS UAs and for linear models such as speech and sequential navigation.” - Ordering and Orientation
最佳答案
我不确定为什么会这样,但我认为这与滚动以这种方式工作有关 - 它从 DOM 中的第一个元素开始。
根据关于滚动目标的 MDN(https://developer.mozilla.org/en-US/docs/Web/Events/scroll):
The event target (the topmost target in the DOM tree).
但这里有一个小技巧可以解决它:
将元素 0 添加到列表顶部 <div class="item a0">000</div>
然后执行以下操作:
btn.addEventListener('click', () => {
list.classList.toggle('reversed');
if(list.classList.contains('reversed') ){
list.children[0].style.order = 100;
} else {
list.children[0].style.order = 0;
}
list.children[0].scrollIntoView();
});
关于javascript - 为什么切换 flex-direction 时顺序最低的元素会滚动到视口(viewport)中?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50812999/