【问题标题】:Safari position:sticky not working in an overflow:auto elementSafari 位置:粘性在溢出中不起作用:自动元素
【发布时间】:2019-01-18 10:33:21
【问题描述】:

根据CanIUse,Safari 和position:stickyoverflow:auto 元素中存在一个已知问题:

将溢出设置为自动的父级将阻止 position:sticky 在 Safari 中工作

但是,这正是我需要的用例。我有一个可滚动的 div,它被细分为两列。右列应该是粘性的并且永远不会移动,即使滚动整个 div 也是如此。我在右列上使用position:sticky 的原因是我希望用户仍然能够使用右列上的光标滚动左列。这是我发现唯一有效的解决方案。

Firefox / Chrome 的工作示例如下: http://cssdeck.com/labs/zfiuz4pc 滚动时橙色区域保持固定,但在 Safari 中不会。

上面的例子对我的问题有一些不必要的包装,但我想尽可能地复制我想让这段代码在其中工作的环境。它的基本要点是我有这个:

<div class="modal-content">
  <div class="left-content">
  </div>
  <div class="sticky-element">
  </div>
</div>

还有 CSS:

.modal-content {
  display: flex;
  overflow: auto;
  flex-flow: row nowrap;
}

.left-content {
  flex: 0 0 300px;
}

.sticky-element {
  position: sticky;
  top: 0;
  right: 0;
  width: 200px;
}

同样,这在 FF/Chrome 中有效,但在 Safari 中无效。有没有办法让它在所有浏览器中工作?或者,即使将鼠标光标悬停在粘性元素上,我也可以使用其他方法来保持可滚动性?

【问题讨论】:

    标签: css safari overflow sticky


    【解决方案1】:

    只需添加position: -webkit-sticky;

    【讨论】:

    • @debanjanB 你是对的,这是我的解释。目前,Safari 仅支持前缀为-webkit- 的此功能。也许这个链接会帮助你理解caniuse.com/#search=sticky
    • 同样对于 Safari,粘性元素需要是块级元素(或使用display: block)。我试图让&lt;button&gt; 具有粘性,但它在Safari 中不起作用,因为按钮默认为inline-block
    【解决方案2】:

    display: block 添加到.sticky-element 对我有用,而无需添加position: -webkit-sticky。在this Codepen 找到此解决方案。

    【讨论】:

    • 谢谢伙计,我在 Safari 中遇到了 Sticky/Position Bottom 的问题……而 Sticky 元素上的 display: block; 很有效!不知道为什么,但似乎已经完成了这项工作!
    • FWIW 我实际上是一个女人 :) 真的很高兴它对你有用,这是一个很好的解决方案!
    【解决方案3】:

    我从其他人那里得到了这个解决方案:

    http://cssdeck.com/labs/bu0nx69w

    基本上,在右侧面板中使用 position:fixed 而不是 position:sticky。关键是在父 div 中也有 will-change:transform(在上面的示例中,在 .modal-content 中),因此 position:fixed 相对于该父级而不是视口变得固定。这是一个巧妙的小技巧

    【讨论】:

    • 您可能已经解决了您的用例,但您找到sticky 不起作用的原因了吗?
    • @Laura 这只是 Safari 的粘性实现。在 Safari 无法处理的 overflow:auto;position:sticky 的特定场景中,它根本不起作用。因此,这个解决方法使用 position:fixed 代替。
    • 谢谢这对我有用,我有一个更复杂的布局,第一列和最后一列是静态的,如果有太多中间列需要水平滚动,整个第一行需要贴在屏幕顶部。我最终对中间列使用了这个技巧,并且能够保持第一列和最后一列的顶行粘性。
    • 不幸的是,由于z-index: -1,这消除了粘性元素中的交互性。不过这是一个不错的技巧。
    【解决方案4】:

    我也遇到过类似情况:

    <div scroll>
        <div sticky />
        <list />
    </div>
    

    只需用 div 包裹滚动内容即可:

    <div scroll>
        <div>
           <div sticky />
           <list />
        </div>
    </div>
    

    【讨论】:

      【解决方案5】:

      如果您的父元素有overflow: hiddenposition: sticky 将不起作用。有了这个sticky 设置,它将自动将您的元素从relative to actual fixed 转换为文档的上边框。

      【讨论】:

        【解决方案6】:

        此特定情况的另一种解决方案,只要您不需要模式最右侧的滚动条即可。

        由于您的粘性元素与您的.modal-content 高度相同,您可以从.sticky-element 中完全删除粘性元素。首先,从.modal-content 中删除overflow:auto,然后将该样式添加到.left-content,因为那是您想要滚动的部分。

        【讨论】:

        • 在发布此内容后立即实现,OP 希望能够在右侧的固定部分上方滚动左侧。这也不允许。
        【解决方案7】:

        我必须在下面使用它才能使其在 Chrome 和 Safari 中都能正常工作:

        position: sticky;
        position: -webkit-sticky;
        display: block;
        

        【讨论】:

          【解决方案8】:

          我现在无法真正为 safari 测试这个,但在创建粘性页脚时,这一直是我的替代方案:

          <!DOCTYPE html>
          <html>
          <head>
              <title>sticky side div</title>
              <style type="text/css">
                  .maindiv{
                      position: relative;
                      display: inline-block;
                      background-color: forestgreen;
                      width: calc(100vw - 150px);
                      height: 100%;
                      overflow: auto;
                  }
                  .sidediv{
                      position: fixed;
                      display: inline-block;
                      background-color: lightyellow;
                      float: right;
                      width: 100px;
                      height: 100%;
                  }
              </style>
          </head>
          <body>
              <div class="maindiv">
                  Lorem 45    
              </div>
              <div class="sidediv">
                  Lorem 30
              </div>
              <div class="maindiv">
                  Lorem 100
              </div>
              <div class="maindiv">
                  Lorem 900
              </div>
          </body>
          </html>
          

          一旦你知道你的正确内容的宽度添加一点像素,然后使用 css calc function 确保其他 div 不会流入它

          在 Safari 7 中还有一个已知的 vh 和 vw 错误。您可以通过设置高度来修复它:继承父级具有 vh 高度或 vw 宽度的#child 元素

          但如果您不支持跨浏览器,我最好的建议是使用CSS Grids

          【讨论】:

          • 我试过你的标记,但它只能按原样工作。但是,如果我使用position:absolute 添加父元素,则右侧面板的位置不正确。我发布了一个刚刚从其他人那里得到的适合我需要的解决方案。
          猜你喜欢
          • 2020-04-03
          • 2016-01-03
          • 2021-11-27
          • 2022-08-17
          • 1970-01-01
          • 2019-02-28
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多