Safari浏览器details/summary元素内部CSS过渡效果失效问题求助
解决方案
核心问题根源
- 所有浏览器内置的details默认样式规则:
details:not([open]) > :not(summary)会被自动设为display: none,元素直接退出渲染流,过渡动画自然无法触发;你在开发者工具手动改属性时元素始终处于可渲染状态,所以过渡正常。 - Safari对details的open/close状态切换有特殊的DOM重排逻辑,未开启硬件加速的3D过渡会被直接中断。
- 你给背面元素用了@keyframes动画,仅在添加
[open]属性时生效,移除属性时没有对应的过渡规则,所以翻回正面会直接跳转。
核心调整点
- 覆盖details的默认显隐规则,让背面元素永久处于
display: block状态,依赖backface-visibility: hidden控制不可见状态,避免过渡被打断 - 把背面元素的动画逻辑换成和正面统一的transition规则,保证正反切换都有过渡
- 给所有参与3D变换的元素添加
will-change: transform强制开启硬件加速,兼容Safari的渲染逻辑 - 补全缺失的定位属性避免不同浏览器的偏移问题
修改后可运行代码
CSS代码
body { width: 100%; height: 100vh; /* 改成vh保证占满视口高度 */ display: flex; align-items: center; justify-content: center; background-color: #fefefe; perspective: 1000px; margin: 0; font-size: 1.25rem; line-height: 1.875rem; } html * { box-sizing: border-box; } details { width: 300px; height: 400px; transform-style: preserve-3d; -webkit-transform-style: preserve-3d; position: relative; cursor: pointer; will-change: transform; } .front, .back, summary:before { position: absolute; width: 100%; height: 100%; top: 0; left: 0; padding: 1rem; backface-visibility: hidden; -webkit-backface-visibility: hidden; transition: all .75s cubic-bezier(0.52, 0.02, 0.28, 1); -webkit-transition: all .75s cubic-bezier(0.52, 0.02, 0.28, 1); will-change: transform; } .front, summary:before { background: white; border-radius: 9px; border: 3px solid orange; box-shadow: 0 0 32px -8px rgba(0, 0, 0, 0.33); } summary { list-style: none; position: absolute; width: 100%; height: 100%; top: 0; left: 0; transform-style: preserve-3d; -webkit-transform-style: preserve-3d; } summary:before { border-color: blue; content: ''; box-sizing: border-box; background: none; transform: rotateY(180deg); -webkit-transform: rotateY(180deg); } .front { background-color: orange; color: white; } summary::-webkit-details-marker, summary::marker { display: none; } .back { overflow-y: scroll; pointer-events: none; transform: rotateY(180deg); -webkit-transform: rotateY(180deg); display: block !important; /* 覆盖details默认的display:none规则 */ } .back p { margin: 0; } details[open] .front { transform: rotateY(180deg); -webkit-transform: rotateY(180deg); } details[open] .back { transform: rotateY(360deg); -webkit-transform: rotateY(360deg); pointer-events: auto; /* 打开状态下允许滚动背面内容 */ } details[open] summary:before { transform: rotateY(360deg); -webkit-transform: rotateY(360deg); }
HTML代码和原代码一致,无需修改
<html> <body> <details> <summary> <div class="front">Front of Card</div> </summary> <div class="back"> <p>Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur.</p> </div> </details> </body> </html>
效果说明
修改后代码在Chrome、Safari都可以正常实现正反双向平滑翻转,翻回正面时不会出现文字提前消失的问题,背面内容可正常滚动。
内容的提问来源于stack exchange,提问作者chrisrooke
相关产品推荐
相关产品推荐

