使用-webkit-transform时固定的位置不起作用


155

我正在使用-webkit-transform(和-moz-transform / -o-transform)来旋转div。还添加了固定位置,以便div与用户一起滚动。

在Firefox中工作正常,但在基于Webkit的浏览器中却坏了。使用-webkit-transform后,固定的位置不再起作用!那怎么可能?


4
演示页面通常可以帮助人们回答问题-如果您不想链接到站点,jsbin.com可以使您创建临时页面来说明问题。
Rich Bradshaw

jsfiddle.net是临时编辑容器的另一个很好的例子。
凯尔(Kyle)2010年

@Rich Bradshaw jsbin.com非常好。直到现在才知道。我的大多数项目都是在本地运行的,因此下一次将使用它。Tnx
iSenne

7
根本无法在Firefox 中正常工作
vsync 2014年

3
在2017年仍然是一个问题。似乎他们仍然坚持“这是功能而不是错误!” 参数...
马克斯

Answers:


87

经过一番研究,出现了一个错误报告的Chromium网站上关于这个问题,到目前为止Webkit的浏览器无法对这两种效应一起在同一时间呈现。

我建议将一些仅Webkit的CSS添加到样式表中,并使转换后的div成为图像并将其用作背景。

@media screen and (-webkit-min-device-pixel-ratio:0) {
  /* Webkit-specific CSS here (Chrome and Safari) */

  #transformed_div {
    /* styles here, background image etc */
  }
}

因此,现在您必须以老式的方式进行操作,直到Webkit浏览器赶上FF。

编辑:截至10/24/2012,该错误尚未解决。


这似乎不是错误,而是规范的一个方面,这是由于这两种效果需要单独的坐标系和堆叠顺序。如这个答案中所解释


34
甚至多年以后,仍然没有解决。真伤心
Amalgovinus 2015年

9
根据这个答案,这不是错误,而是规范的一部分。
MichaelRushton 2015年

15
坐下来观看-我敢打赌它将活到它的10周年纪念日
lzl124631x

29
2017年8月30日,船长的日志。我们还遇到了奇怪的异常,很久以前其他机长对此进行了描述。解决方案仍有待实施。
Luoruize

14
这是我父亲的父亲警告我的错误。
danjones_mcr

96

CSS变换规格解释这种行为。带有转换的元素充当固定位置后代的包含块,因此position:fixed在具有转换的对象下不再具有固定的行为。

当应用于相同元素时,它们确实起作用。元素将被定位为固定,然后进行转换。


9
这是唯一有用且正确的答案。停止翻译父元素,并翻译固定元素属于其中的子元素。这里是我的小提琴:的jsfiddle
福尔克

2
如果我也想转换固定元素怎么办?
2016年

7

对于那些发现自己的背景图片在Chrome中消失的人,因为背景附件存在相同的问题:已修复;已修复;-这是我的解决方案:

// run js if Chrome is being used
if(navigator.userAgent.toLowerCase().indexOf('chrome') > -1) {
    // set background-attachment back to the default of 'scroll'
    $('.imagebg').css('background-attachment', 'scroll');

    // move the background-position according to the div's y position
    $(window).scroll(function(){

        scrollTop = $(window).scrollTop();
        photoTop = $('.imagebg').offset().top;
        distance = (photoTop - scrollTop);
        $('.imagebg').css('background-position', 'center ' + (distance*-1) + 'px');

    });
}  

6

对我有用的东西(有点hacky)是position:sticky

.fixed {
     position: sticky;
}

5
updates.html5rocks.com/2012/08/…啊,是的,但是似乎还没有得到很好的支持
coiso 2014年

1
粘性不同。主要的问题是,固定后,我们想忽略容器的位置(非常有用。例如,对于不透明动画),我无法相信这个错误在几年后仍然存在。可怕。
FlorianB 2016年

6

2016年8月,固定位置和动画/变换仍然是一个问题。对我而言唯一有效的解决方案是为子元素创建动画,而这需要花费更长的时间。


请回答新问题。这些问题比2010年问问题的人更需要您。他们现在一定已经解决了问题,您认为吗?这个问题也已经有一个可以接受的答案。
Umair Farooq,2016年

5
不!这仍然是一个问题……提出这个问题的人可能已经找到了另一个解决方案,但是我找到这个线程是有原因的。
defligra

如你所愿。我在评论人们的第一个问题时留下了评论。由于您是今天才加入的,这是您的第一个答案,也是一个较晚的答案,所以这就是为什么我留下这个评论。我没有投票。这对您来说是个好机会。
Umair Farooq

1
@UmairFarooq可能问另一个问题是没有用的,因为它可能被标记为重复。我来到这里只是用Google搜索,我发现这个问题也很有用,defligra的答案也是如此。
koMah

3

实际上,我找到了另一种解决此“错误”的方法:

我有容器元素,其中包含css3动画的页面。当页面完成动画时,css3属性的值为:transform:translate(0,0);。因此,我刚刚删除了这一行,一切都按预期进行-位置:固定显示正确。当将css类应用于翻译页面时,将添加translation属性,并且css3动画也将起作用。

例:

.page {
     top: 50px;
     position: absolute;
     transition: ease 0.6s all;
     /* -webkit-transform: translate(0, 0); */
     /* transform: translate(0,0); */
 }
 .page.hide {
     -webkit-transform: translate(100%, 0);
     transform: translate(-100%, 0);    
 }

演示:http//jsfiddle.net/ZWcD9/


1
对我来说,事实是,在包含固定元素的包装器上使用了这些样式可以防止固定样式发粘:-webkit-perspective:1000;-webkit-transform-style:保留3d; 取消这些,一切正常。无论如何,它们是可疑的优化!
Amalgovinus

无论如何,删除转换可能是迄今为止最好的解决方法。淡入淡出之类的东西一旦完成,应可移除而不影响元素的外观。实际上,我不确定是否有一个transformX(0)会影响渲染性能,如果有的话。它要么被忽略,要么损害性能,或者可以通过强制某种3D加速来使其更好。谁知道。无论如何,一旦完成动画,或者甚至在将固定元素添加到动画之前,都可以简单地删除用于转换的CSS类。
Triynko

1

在我的phonegap项目中,webkit转换-webkit-transform:translateZ(0); 像魅力一样运作。它已经在chrome和safari中运行,而不仅仅是移动浏览器。还有一个问题是在某些情况下WRAPPER DIV尚未完成。对于浮动DIV,我们会应用清晰的类。

<div class="Clear"></div> .Clear, .Clearfix{clear:both;}


1

在尝试使用react-swipeable-views(rsw)实现react-color时遇到了这个问题。对我来说,问题是rsw应用于translate(-100%, 0)选项卡面板,该选项卡破坏了全屏上添加的默认固定位置div,单击该默认固定位置div将关闭颜色选择器模型。

对我来说,解决方案是对固定元素应用相反的变换(在这种情况下translate(100%, 0),此问题解决了我的问题。我不确定这在其他情况下是否有用,但我认为还是可以分享。

这是显示我上面描述的示例:

https://codepen.io/relativemc/pen/VwweEez


0

-webkit-transform固定元素添加可以为我解决问题。

.fixed_element {
   -webkit-transform: translateZ(0);
   position: fixed;
   ....
} 

20
那对我没用。您能创建一个演示它的工作原理吗?
Alex

4
这为我在Chrome FWIW中解决了一个问题。谢谢罗恩。
克里斯,

3
谢谢,这解决了我一个问题。救了我一命!
styke

1
@Neil Monroe,Android 2.3是一个全新的故事。它根本不支持固定位置:)
Wiseman 2013年

8
这是一个小提琴translateZ(0) 无法使用。的确,有时它会起作用,我见过一些可行的场合。但是我仍然不能缩小范围。
Zequez 2014年

0

这是我在所有经过测试的浏览器和移动设备(Chrome,IE,Firefox,Safari,iPad,iphone 5和6,Android)上适用的功能。

img.ui-li-thumb {
    position: absolute;
    left: 1px;
    top: 50%;

    -ms-transform: translateY(-50%);
    -webkit-transform: translateY(-50%);
    -moz-transform: translateY(-50%);
    -o-transform: translateY(-50%);
    transform: translateY(-50%);
}

2
为什么要下票?如果您提供关于您为什么不赞成我的答案的评论,那将是很好的。
默夫

0

如果将变换应用于任何祖先,则元素的固定位置将被破坏。

<div style='position:fixed;-.*-transform:scale(2)'>...</div> //ok

<div style='-.*-transform:scale(2)'>
      <div style='position:fixed'>...</div> // broken
</div>

0

如果您可以使用javascript作为选项,则可以将其定位为相对于窗口的位置固定元素(位于转换后的元素中)时的变通办法:

  let fixedEl // some node that you is position 
              // fixed inside of an element that has a transform

  const rect = fixedEl.getBoundingClientRect()
  const distanceFromWindowTop = rect.top
  const distanceFromWindwoLeft = rect.left
  let top = fixedEl.offsetTop
  let left = fixedEl.offsetLeft

  if(distanceFromWindowTop !== relativeTop) {
    top = -distanceFromWindowTop
    fixedEl.style.top = `${top}px`
  }

  if(distanceFromWindowLeft !== relativeLeft) {
    left = -distanceFromWindowLeft
    fixedEl.style.left = `${left}px`
  }

当然,您还必须调整高度和宽度,因为fixedEl将基于容器来计算高度和宽度。这取决于您的用例,但这将使您可以预测地将某物位置固定为固定位置,而不管其容器是什么。


0

在元素变形时添加动态类。$('#elementId').addClass('transformed')。然后继续在CSS中声明,

.translatX(@x) { 
     -webkit-transform: translateX(@X); 
             transform: translateX(@x);
      //All other subsidaries as -moz-transform, -o-transform and -ms-transform 
}

然后

#elementId { 
      -webkit-transform: none; 
              transform: none;
}

然后

.transformed {
    #elementId { 
        .translateX(@neededValue);
    }
}

现在位置:在子元素上具有top和z-index属性值时固定,可以正常工作并保持固定,直到父元素变形为止。恢复转换后,子元素将再次按固定方式弹出。如果您实际上使用的导航侧栏可以在单击时切换打开和关闭,并且应该有一个选项卡集,当您向下滚动页面时该选项卡集应该保持粘性,这应该可以缓解这种情况。


0

就我而言,我发现我们不能在transform:translateY()之前使用transform:translateX()。如果要同时使用,则应该使用transform:translate(,)。


-1

请不要投票,因为这不是确切的答案,但可以帮助某人,因为这是关闭转换的快速方法。如果您确实不需要对父项进行转换,并且希望固定位置再次起作用:

#element_with_transform {
  -webkit-transform: none;
  transform: none;
}

1
就像问题的标题一样
尤金·潘科夫

@EugenePankov标题中看不到“ none”。这就是解决我的问题的方法,通常没有人建议关闭它。尽管这并不是该问题的确切答案,但是它可以帮助那些不想使用转换的人,并且该转换来自另一个库。因此,我不想投反对票,但请不要投反对票。我将编辑我的问题,说我不想投票。
makkasi
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.