定位粘性水平滚动,显示网格在 Firefox 和 Safari 中表现得很奇怪



我正在尝试在 React 中创建一个可重用的 Table 组件,该组件具有粘性列(水平滚动时(,带有display: gridposition: sticky

我在Chrome中开始实现,一切都按预期工作,所以我检查了Firefox和Safari组件在那里的工作方式。不幸的是,Firefox和Safari处理position: sticky的方式与Chrome不同。


例:

为了简洁起见,这里有一个Codepen,可以在其中检查问题。


我发现了什么:

为了进行测试,我使表中的第一列和最后两列具有粘性。我发现Firefox将最后两列的thtd元素渲染为position: absolute

每当我将表格大小调整为较小的宽度时,表格的scrollWidth(应该是所有列width的总和(clientWidth(应该是table元素的width(Firefox 上是相同的,在Chrome 上是不同的值

例如:

// Firefox & Safari
table.scrollWidh = 657
table.clientWidth = 657
// Chrome
table.scrollWidth = 800
table.clientWidth = 657

TBH,我不确定我是否同时在Firefox和Safari中发现了一个错误,或者我现在应该信任哪个浏览器。或者我的实现中缺少一个 CSS 属性。

你遇到过这个吗?如果我错过了什么,你有提示吗?

终于,我能够解决问题。该解决方案需要一些JS修改。

问题是在Firefox和Safari上,table元素的scrollWidth不包含列的宽度,该列具有position: stickyCSS规则.
为了解决这个问题,我在table中引入了一个::before伪元素。 样式定义现在如下所示:

table {
...
position: relative;
}
table::before {
position: absolute;
top: 0;
left: 0;
height: 100%;
z-index: -1;
}

我计算所有列宽度的总和并将其应用于伪元素。

之后,scrollWidth也将在Firefox和Safari上具有正确的值。

不幸的是,这个问题没有纯粹的CSS解决方案。幸运的是,无论如何我都必须测量列宽,因为我需要它们来获得正确的leftright值。

最新更新