Folding the DOM
主要内容
- 背景与动机:
- 作为前端开发人员,作者习惯性地将 CSS 视为一组二维层,很少在三维空间中移动元素。然而,浏览器内置了强大的 3D CSS 引擎,该引擎可以实现复杂的 3D 效果。
- 本文目标:
- 利用 3D CSS 引擎展示一个折叠图片的效果,这个效果可以在图片预加载、点击查看图片动画和 JS 游戏开发中使用,该教程针对 React 设计,但也可移植到其它前端框架和原生 JS/CSS。
- 实现技巧:
- 由于 DOM 本身没有折叠节点的原语,需要通过两张图片模拟一张图像的折叠效果。两张图片各占高度的 50%,并调整背景位置,使其看起来像一张图片。底部图片使用 CSS 属性进行旋转,模拟折叠效果。
- 所需 CSS 属性:
- Transform:用于旋转图像,允许在 X 轴上旋转。
- Perspective:给父容器添加透视效果,使变换看起来更真实,代表观察者到物体的距离。
- Transform Origin:定义元素的旋转中心,可以设置为顶部或底部。
- 实际实现:
- 使用状态管理和几个共享 CSS 样式创建了一个
Foldable
组件。通过单独调整上半部分和下半部分的背景位置和旋转效果,实现图片折叠动画,并为折叠设置了滑块控制。
- 无障碍问题及解决方案:
- 由于使用
div
设置背景图片,会导致屏幕阅读器无法识别。为了解决这个问题,折叠组件的上半部分改用 img
元素,并在容器中设定 overflow: hidden
以隐藏溢出部分。
- 细节打磨:
- 添加副面背景元素,该背景有轻微透明效果,使其看起来像一张薄的纸。通过设置
backface-visibility
和 transform-style: preserve-3d
实现背面不可见,并调整翻转元素的 Z 轴位置,处理闪烁问题。最后引入 React Spring
实现滑块拖动的平滑动画效果。
- 效果细节:
- 添加阴影效果,使底部部分在折叠的前 90 度变暗,模拟光源效果。
- 通过 Z 轴平移量的调整,给卡片添加厚度效果。
- 总结:
- 尽管实现这样的 3D 效果需要一定的复杂度,但 React 的可重用性使得该效果可以在未来项目中轻松复用。由于这个效果在实际应用中比较少见,因此对用户具有更强的视觉冲击力。文章还探讨了将该效果应用于其它类型元素的可能性,如表单折叠。
总结
本文介绍了如何利用 3D CSS 变换和 React,实现逼真的图片折叠效果。通过细致的技巧分析和实际代码演示,展示了从基本折叠效果到无障碍优化再到效果细节打磨的全过程。这种特殊的 3D 动画效果,不仅提升了页面动画的趣味性,而且通过可重用组件的方式使其更容易在未来项目中使用。