• 利用SVG滤镜实现水波倒影效果


            SVG滤镜用来增加对SVG图形的特殊效果。多种滤镜巧妙结合起来可以实现很棒的视觉效果。下面利用svg的feTurbulence滤镜和feDisplacementMap来模拟真实的水波倒影特效。效果如下图

     代码并不复杂,首先设置两张图片:

    1. <div class="container">
    2. <div class='wrap'>
    3. <img src="./p.jpg"><br/>
    4. div>
    5. <div class='wrap'>
    6. <img src="./p.jpg" class="reflect">
    7. div>
    8. div>

    设置样式,将倒影图旋转,调整到合适的位置:

    重点是滤镜的样式:filter:url(#displacementFilter);

    在文档中定义svg滤镜:

    1. <svg width="0" height="0" style="posiotion:absolute;">
    2. <filter id="displacementFilter">
    3. <feTurbulence type="turbulence" baseFrequency="0.01 .1" numOctaves="1" result="turbulence" seed="53" />
    4. <feDisplacementMap in2="turbulence" in="SourceGraphic" scale="20" xChannelSelector="R" yChannelSelector="B" />
    5. filter>
    6. svg>

    此时,得到的效果是静态的 ,但已经得到了倒影的效果。

     下面通过设置动画让倒影波动起来,添加动画:

    至此,整体效果达成。

            简短的代码实现了真实的水波效果,这主要归功于svg的强大滤镜功能。SVG滤镜用来增加对SVG图形的特殊效果。这里重点说说我们用到的两个滤镜feTurbulence和feDisplacementMap。

            feTurbulence滤镜

    该滤镜利用 Perlin 噪声函数创建了一个图像。它实现了人造纹理比如说云纹、大理石纹的合成。除了svg滤镜的通用属性外,该滤镜支持5种专属属性的设置:

    feTurbulence参数
    属性默认值说明
    baseFrequency0柏林噪波函数的基频参数
    numOctaves1柏林噪波函数的八度音阶数。
    seed0柏林澡波函数生成的伪随机数的开始数字。
    stitchTilesnoStitch柏林噪波瓷砖在边界处的行为。
    typeturbulence以噪声函数还是湍流函数执行过滤

    以上参数看起来很抽象,我们通过示例来体验每个参数的作用:

    baseFrequency

    1. <svg viewBox="0 0 420 200" xmlns="http://www.w3.org/2000/svg">
    2. <filter id="noise1" x="0" y="0" width="100%" height="100%">
    3. <feTurbulence baseFrequency="0.025" />
    4. filter>
    5. <filter id="noise2" x="0" y="0" width="100%" height="100%">
    6. <feTurbulence baseFrequency="0.05" />
    7. filter>
    8. <rect x="0" y="0" width="200" height="200" style="filter: url(#noise1);" />
    9. <rect x="0" y="0" width="200" height="200" style="filter: url(#noise2); transform: translateX(220px);" />
    10. svg>

    效果:

    如果提供两个数字,第一个数字表示水平方向上的基频,第二个数字表示垂直方向上的基频。如果提供了一个数字,则该值同时用于x和y。不支持使用负值。

     numOctaves

    当我们设置了这个属性之后,算法会在原来的噪声函数上叠加若干个频率不同的他自己,形成细节更加丰富的噪声,看一下numOctaves增加时的动态效果。倍频程是由其频率和振幅定义的噪声函数。湍流是通过增加频率和降低振幅来累积几个八度音阶而形成的。八度音阶越高,噪音看起来就越自然。

    1. <svg viewBox="0 0 420 200" xmlns="http://www.w3.org/2000/svg">
    2. <filter id="noise1" x="0" y="0" width="100%" height="100%">
    3. <feTurbulence baseFrequency="0.025" numOctaves="1" />
    4. filter>
    5. <filter id="noise2" x="0" y="0" width="100%" height="100%">
    6. <feTurbulence baseFrequency="0.025" numOctaves="3" />
    7. filter>
    8. <rect x="0" y="0" width="200" height="200" style="filter: url(#noise1);" />
    9. <rect x="0" y="0" width="200" height="200" style="filter: url(#noise2); transform: translateX(220px);" />
    10. svg>

    效果:

    seed 

    seed是种子的意思,这是每一个随机数算法都需要用到的一个输入,所有的伪随机数算法中,当输入的种子一样的时候,输出总是一致的。

    stitchTiles

    该属性定义了对平铺边界处实现平滑过渡,可选值为noStitch | stitch。

    1. <svg viewBox="0 0 420 200" xmlns="http://www.w3.org/2000/svg">
    2. <filter id="noise1" x="0" y="0" width="100%" height="100%">
    3. <feTurbulence baseFrequency="0.025" stitchTiles="noStitch" />
    4. filter>
    5. <filter id="noise2" x="0" y="0" width="100%" height="100%">
    6. <feTurbulence baseFrequency="0.025" stitchTiles="stitch" />
    7. filter>
    8. <rect x="0" y="0" width="100" height="100" style="filter: url(#noise1);" />
    9. <rect x="0" y="0" width="100" height="100" style="filter: url(#noise1); transform: translate(100px, 0);" />
    10. <rect x="0" y="0" width="100" height="100" style="filter: url(#noise1); transform: translate(0, 100px);" />
    11. <rect x="0" y="0" width="100" height="100" style="filter: url(#noise1); transform: translate(100px, 100px);" />
    12. <rect x="0" y="0" width="100" height="100" style="filter: url(#noise2); transform: translate(220px, 0);" />
    13. <rect x="0" y="0" width="100" height="100" style="filter: url(#noise2); transform: translate(320px, 0);" />
    14. <rect x="0" y="0" width="100" height="100" style="filter: url(#noise2); transform: translate(220px, 100px);" />
    15. <rect x="0" y="0" width="100" height="100" style="filter: url(#noise2); transform: translate(320px, 100px);" />
    16. svg>

    效果:

     type

    可选值 fractalNoise | turbulence

    turbulence是指将柏林函数进行合成时,只取函数的绝对值,合成后的函数在0处不可导,其图像会有一些尖锐效果,形似湍流。fractalNoise则是在原来的噪声中叠加白噪声,让最终的结果呈现出高斯模糊的效果。

    feDisplacementMap滤镜

    映射置换滤镜,该滤镜用来自图像中从in2 (en-US)到空间的像素值置换图像从in到空间的像素值。
     

    属性默认值取值说明
    inSourceGraphicSourceGraphic | SourceAlpha | BackgroundImage | BackgroundAlpha | FillPaint | StrokePaint | 自定义的滤镜的原始引用in 属性标识输入的源
    in2 

    第一个过滤器原语的源图形,否则为上一个过滤器原形的结果

    SourceGraphic | SourceAlpha | BackgroundImage | BackgroundAlpha | FillPaint | StrokePaint | 自定义的滤镜的原始引用in2属性标识给定过滤器原语的第二输入。它的工作原理与in属性完全相同。
    scale0缩放比例 通常使用正数值处理,值越大,偏移越大
    xChannelSelectorAR | G | B | A使用in2中的哪个颜色通道沿x轴置换像素。
    yChannelSelectorAR | G | B | A属性指示使用in2中的哪个颜色通道沿y轴置换像素。

    feDisplacementMap 是一个位置替换滤镜,就是改变元素和图形的像素位置的。遍历原图形的所有像素点,使用feDisplacementMap重新映射替换一个新的位置,形成一个新的图形。feDisplacementMap滤镜在业界的主流应用是对图形进行形变,扭曲。

    P'(x,y) ← P( x + scale * (XC(x,y) - 0.5), y + scale * (YC(x,y) - 0.5))

    •  P'(x,y)指的是转换之后的x, y坐标。
    •  x + scale * (XC(x,y) - 0.5), y + scale * (YC(x,y) - 0.5)指的是具体的转换规则。
    •  XC(x,y)表示当前x,y坐标像素点其X轴方向上设置的对应通道的计算值,范围是0~1。
    •  YC(x,y)表示当前x,y坐标像素点其Y轴方向上设置的对应通道的计算值,范围是0~1。
    •  -0.5是偏移值,因此XC(x,y) - 0.5范围是-0.5~0.5YC(x,y) - 0.5范围也是-0.5~0.5
    •  scale表示计算后的偏移值相乘的比例,scale越大,则偏移越大。

     简单讲就是根据设定的通道颜色对原图的x, y坐标进行偏移。

  • 相关阅读:
    【TestNG学习(三)套件测试】
    C++内存管理
    4.华为三层交换机 配置VLAN 基于全局开启DHCP
    ELK日志分析系统+ELFK(Filebeat)
    从零开始基于Archlinux 安装 containerd + k8s
    记 QT => ubuntu下QT可编译通过不可以运行图形界面
    【Vue】vue先转化文章内容再去除标签 vue filters过滤器去除标签 js提取文字内容
    知识管理系统如何提升企业核心竞争力
    网络安全(黑客)自学
    React——相关js库以及使用React开发者工具调试
  • 原文地址:https://blog.csdn.net/u014399368/article/details/126367923