• 使用CSS实现《声生不息》节目Logo


    声明:本文涉及图文和模型素材仅用于个人学习、研究和欣赏,请勿二次修改、非法传播、转载、出版、商用、及进行其他获利行为。

    背景

    《声生不息》 是芒果TV、香港电视广播有限公司和湖南卫视联合推出的港乐竞唱献礼节目,听着音乐仿佛回到了那个令人怀念的港风席卷整个亚洲的年代。

    该节目 Logo 采用经典红蓝配色,无限符号 造型,满满的设计感。本文在仅采用原生 CSS 的情况下,尽量还原实现该 Logo 造型,本文内容虽然非常简单,但是用到的知识点挺多的,比如:repeating-linear-gradientclip-pathbackground-clipWindow.getComputedStyle()CSSStyleDeclaration.getPropertyValue() 等。

    效果

    先来看看实现效果吧。

    点击右上角的 半圆 形状,页面主体可切换为白色。

    在线预览

    Github:https://dragonir.github.io/shengshengbuxi/
    Codepen:https://codepen.io/dragonir/full/OJQRBad

    实现

    开始之前,先把 Logo 中用到的主要颜色作为CSS变量,后续会在多处用到这几种颜色,并要通过变量实现页面主体颜色切换功能。

    :root {
      --black: #010101;
      --red: #F66034;
      --blue: #0A68DF;
    }
    

    步骤0:第一个圆

    观察 Logo 原型可以发现,第一个 纯红色条纹样式效果,可以通过 repeating-linear-gradient 实现条纹背景效果,并设置伪元素 ::after 为背景黑色实现圆环样式。

    <div class="logo">
      <div class="cycle cycle_1"></div>
    </div>
    
    .cycle {
      height: 500px;
       500px;
      border-radius: 50%;
      position: relative;
      box-sizing: border-box;
    }
    .cycle_1 {
      z-index: 2;
      background: var(--red);
      background: repeating-linear-gradient(180deg,var(--red),var(--red) 12px, var(--black) 0,  var(--black) 22px);
      border: 12px solid var(--black);
    }
    .cycle_1::after {
      content: '';
      display: inline-block;
      height: 200px;
       200px;
      background: var(--black);
      position: absolute;
      top: 50%;
      left: 50%;
      margin-top: -100px;
      margin-left: -100px;
      border-radius: 50%;
      z-index: 3;
    }
    

    repeating-linear-gradient

    repeating-linear-gradient 创建一个由重复线性渐变组成的 <image>,和 linear-gradient 采用相同的参数,但它会在所有方向上重复渐变以覆盖其整个容器。

    语法

    repeating-linear-gradient([ <angle> | to <side-or-corner> ,]? <color-stop> [, <color-stop>]+ )
                                \---------------------------------/ \----------------------------/
                                          渐变轴的定义                           色标列表
    
    • <side-or-corner>:描述渐变线的起始点位置。它包含两个关键词:第一个指出垂直位置 leftright,第二个指出水平位置topbottom。关键词的先后顺序无影响,且都是可选的。to top, to bottom, to leftto right 这些值会被转换成角度 0度180度270度90度。其余值会被转换为一个以向顶部中央方向为起点顺时针旋转的角度。渐变线的结束点与其起点中心对称
    • <angle>:用角度值指定渐变的方向或角度。角度顺时针增加。
    • <color-stop>:由一个 <color> 值组成,并且跟随着一个可选的终点位置,可以是一个<percentage> 或者是沿着渐变轴的 <length>

    示例

    // 一个倾斜45度的重复线性渐变, 从蓝色开始渐变到红色
    repeating-linear-gradient(45deg, blue, red);
    // 一个由下至上的重复线性渐变, 从蓝色开始,40%后变绿,最后渐变到红色
    repeating-linear-gradient(0deg, blue, green 40%, red);
    

    每次重复,色标位置的偏移量都是基准渐变长度(最后一个色标和第一个之间的距离)的倍数。因此,最后色标的色值应该与第一个色标的色值保持一致;如果不一致的话,会导致非常突兀的渐变效果。
    与其他渐变一样,线形重复渐变没有提供固定的尺寸;即, 它没有原始尺寸或首选尺寸,也没有首选的比例。它将自适应于对应元素的尺寸。

    步骤1:第二个圆

    添加第二个圆 置于第一个圆 的底层,它的样式是从左到右的径向渐变,通过 linear-gradient 即可实现。

    <div class="logo">
      <div class="cycle cycle_1"></div>
      <div class="cycle cycle_2"></div>
    </div>
    
    .cycle_2 {
      margin-left: -160px;
      background: linear-gradient(to right, var(--red), var(--blue));
      border: 12px solid var(--black);
    }
    .cycle_2::after {
      content: '';
      display: inline-block;
      height: 200px;
       200px;
      background: var(--black);
      position: absolute;
      top: 50%;
      left: 50%;
      margin-top: -100px;
      margin-left: -100px;
      border-radius: 50%;
      z-index: 3;
    }
    

    步骤2:两个圆的重叠部分

    底部重叠部分,使用 clip-path 裁切出一个半圆效果,置于所有最顶层。

    .cycle_2::before {
      position: absolute;
      box-sizing: border-box;
      top: -12px;
      left: -12px;
      content: '';
      display: inline-block;
      height: 500px;
       500px;
      background: var(--red);
      border-radius: 50%;
      -webkit-clip-path: polygon(0 50%, 100% 50%, 100% 100%, 0 100%);
      clip-path: polygon(0 50%, 100% 50%, 100% 100%, 0 100%);
      z-index: 3;
      border: 12px solid var(--black);
    }
    

    clip-path

    clip-path 使用裁剪方式创建元素的可显示区域。区域内的部分显示,区域外的隐藏。

    语法

    // 关键字   值
    // none
    clip-path: none;
    // <clip-source> 值
    clip-path: url(resources.svg#c1);
    // <geometry-box> 值
    clip-path: margin-box;
    clip-path: border-box;
    clip-path: padding-box;
    clip-path: content-box;
    clip-path: fill-box;
    clip-path: stroke-box;
    clip-path: view-box;
    // <basic-shape> 值
    clip-path: inset(100px 50px);
    clip-path: circle(50px at 0 100px);
    clip-path: ellipse(50px 60px at 0 10% 20%);
    clip-path: polygon(50% 0%, 100% 50%, 50% 100%, 0% 50%);
    clip-path: path('M0.5,1 C0.5,1,0,0.7,0,0.3 A0.25,0.25,1,1,1,0.5,0.3 A0.25,0.25,1,1,1,1,0.3 C1,0.7,0.5,1,0.5,1 Z');
    // 盒模型和形状值结合
    clip-path: padding-box circle(50px at 0 100px);
    // 全局值
    clip-path: inherit;
    clip-path: initial;
    clip-path: revert;
    clip-path: revert-layer;
    clip-path: unset;
    
    • <clip-source>:用 url() 引用 SVG<clipPath> 元素
    • <basic-shape>:一种形状,其大小和位置由 <geometry-box> 的值定义。如果没有指定 <geometry-box>,则将使用 border-box 用为参考框。取值可为以下值中的任意一个:
      • inset():定义一个 inset 矩形。
      • circle():定义一个圆形,使用一个半径和一个圆心位置。
      • ellipse():定义一个椭圆,使用两个半径和一个圆心位置。
      • polygon():定义一个多边形,使用一个 SVG 填充规则和一组顶点。
      • path():定义一个任意形状,使用一个可选的 SVG 填充规则和一个 SVG 路径定义。
    • <geometry-box>:如果同 <basic-shape> 一起声明,它将为基本形状提供相应的参考框盒。通过自定义,它将利用确定的盒子边缘包括任何形状边角(如被 border-radius 定义的剪切路径)。几何框盒的可选值:
      • margin-boxmargin box 作为引用框。
      • border-boxborder box 作为引用框。
      • padding-boxpadding box 作为引用框。
      • content-boxcontent box 作为引用框。
      • fill-box:利用对象边界框 object bounding box 作为引用框。
      • stroke-box:使用笔触边界框 stroke bounding box 作为引用框。
      • view-box:使用最近的 SVG 视口 viewport 作为引用框。如果 viewBox 属性被指定来为元素创建 SVG 视口,引用框将会被定位在坐标系的原点,引用框位于由 viewBox 属性建立的坐标系的原点,引用框的尺寸用来设置 viewBox 属性的宽高值。
    • none:不创建剪切路径。

    步骤3:重叠部分优化

    将重叠部分设置为与第二个圆 相同的渐变色,可以产生由第一圆 过渡为第二圆 的错觉。

    .cycle_2::before {
      background: linear-gradient(to right, var(--red), var(--blue));
    }
    

    步骤4:文字

    Logo 文字是从左到右由蓝到红的渐变效果,可以通过将文字的盒背景设置为渐变色,然后通过 background-clip: text 将背景被裁剪成文字的前景色来实现。

    <h1 class="text">声生不息</h1>
    
    .text {
      background: linear-gradient(to right, var(--blue), var(--red));
      -webkit-background-clip: text;
      background-clip: text;
      -webkit-text-fill-color: transparent;
      font-style: italic;
    }
    

    background-clip

    background-clip 设置元素的背景图片或颜色是否延伸到边框、内边距盒子、内容盒子下面。如果没有设置background-imagebackground-color,那么这个属性只有在 border 被设置为非 soild、透明或半透明时才能看到视觉效果,否则本属性产生的样式变化会被边框覆盖。

    语法

    // 关键字         值
    background-clip: border-box;
    background-clip: padding-box;
    background-clip: content-box;
    background-clip: text;
    // 全局值
    background-clip: inherit;
    background-clip: initial;
    background-clip: unset;
    
    • border-box:背景延伸至边框外沿,但是在边框下层。
    • padding-box:背景延伸至内边距 padding 外沿。不会绘制到边框处。
    • content-box:背景被裁剪至内容区 content box 外沿。
    • text:背景被裁剪成文字的前景色(实验性属性)。

    步骤5:点击切换效果

    点击右上角的的半圆形图案 ,可以实现将 Logo彩色切换为纯白色,该功能是通过切换定义在 :root 下的 CSS变量 值实现的,可以通过以下方法实现 CSS变量 值的切换。

    <span class="toggle" id="toggle" title="点击切换颜色"></span>
    

    半圆形图案 的噪点背景效果是通过添加一张噪点图实现。

    .toggle {
      background: linear-gradient(to left bottom, var(--blue), rgba(0, 0, 0, 0)), url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAEAAAABAAgMAAADXB5lNAAAADFBMVEUvLy9eXl6AgICoqKhWH7o7AAAABHRSTlMSEhIS3WyPCwAAA1hJREFUOMsN0M3rDHEcwPH3d3y/4zcr67s1s3bIU62y8nBxcVCf79pZ4WBWsx6TVbvyEKUolJrxmBTj4SecVqE4OTjgIP6D5eC8DkouOJAj19fxhXJCWn811mk1Sp1q0J0q6AoNF7ZQ0uD+74CBj3otoUUEmJc0wqVEr2Ulatp1/6HYA9SGwfn+s6ftD8zsbic1idsPVrfcoQRYSrvbd7PdA7TY6cKcbfrwRXaJaqgTXSfDKd625S7XGB1YraJ0yuatOJmJvf5aqIwYINvBGIr+gZiDl80Qdoh3M1GTfuCzf1+yEetme3loJ3Hf6yijG5S9rRa7XI7Nzu1AYGF5Bd1cNeplTmN8yJpV8kYrpKEIAzXDgbBK2QhhTb37NP4P1aqRZ3ua6DVLb2AKjVpgBkbHie4QGFVqxDcpgL4tlTUMNKKgazpmWC+CkBBkTu59dpl+XikMg+U5izd/9z+KpxcFYvxxs01Vtho32XLZBNRmy8YWQBszOV6ES9r7cvQdshRbKVdfOrDKeyB+MeXsWvMmI95/Pdsp7J5MydZHR9MonithyhIllnSppjGaQRkb7vVyTaqNhLUsVI5I/HEDi3JYWdu+KEgsmkzJXGPZ97wQyqPREfp+vmAvzo3AfhF9HvZS1SiZL9H4pVgfhmofCltJ3wxq9/961Aaqq3HpzsFroqtPe9SVm3Ol5yd3f99TueB46l+9lB/drm4PxXs/4j4j5k6pAzS88njnDp72JijRYlYFRMaxfY8q20pWZjGLdKsCP2YoVYXl9RK1Kp7Xpx8MLYEe+gIWlUDwJNABR0AVAGQ4rfcCrci5YQYZonhi9ckLVrkTeCTeL5+0H7+Lw1baYjGu+6ddepc6qeLc8EhvL3dvf5Xi9maHyrGnCmFXXo7bk83O3C6FFYVDURtfLD4YVUpO011EfYvktpukxpKogevhPViJPC6tmWnOcxkaJYnwOw2zyoYKeAmKIlfpILLxBmOo3yLlkzh5+yTKmkvtrsc3oP8Tx7t8YTms2Be9a0TJNJ21Gb6k5mwY9Vn/P2vRSHu7tiZ2kx6mrMtCoqPG+9w3YWxOw5EZDcszz+tUQhZlq8j8Rw77ynqzi7XaV3kH8x62ScfWdhZpkgX3wWdZcibtbFASgOEfZmfZzbdc/O0AAAAASUVORK5CYII=');
    }
    
    // 获取根元素
    const root = document.querySelector(':root');
    // 创建获取变量值的函数
    const getCssVariable = (key) =>  {
      return getComputedStyle(root).getPropertyValue(key);
    }
    // 创建设置变量值的函数
    const setCssVariable = (key, value) => {
      root.style.setProperty(key, value);
    }
    // 点击切换CSS变量值
    document.getElementById('toggle').addEventListener('click', () => {
      if (getCssVariable('--blue') === '#FFFFFF') {
        setCssVariable('--blue', '#0A68DF');
        setCssVariable('--red', '#F66036');
      } else {
        setCssVariable('--blue', '#FFFFFF');
        setCssVariable('--red', '#FFFFFF');
      }
    }, false);
    

    Window.getComputedStyle()

    Window.getComputedStyle() 方法返回一个对象,该对象在应用 active 样式表并解析这些值可能包含的任何基本计算后,返回元素的所有 CSS 属性的值。

    语法:

    let style = window.getComputedStyle(element, [pseudoElt]);
    
    • 参数
      • element:用于获取计算样式的 Element
      • pseudoElt:可选,指定一个要匹配的伪元素的字符串。必须对普通元素省略或 null
    • 返回值:返回的 style 是一个实时的 CSSStyleDeclaration 对象,当元素的样式更改时,它会自动更新。

    getComputedStyle 可以从伪元素拉取样式信息,如 ::after, ::before, ::marker, ::line-marker

    CSSStyleDeclaration.getPropertyValue()

    CSSStyleDeclaration.getPropertyValue() 接口返回一个 DOMString ,其中包含请求的 CSS 属性的值。

    语法

    var value = style.getPropertyValue(property);
    
    • 参数property 是一个 DOMString,是需要查询的 CSS 属性名称。
    • 返回值valueDOMString,包含查找属性的值。若对应属性没有设置,则返回空字符串。

    步骤6:噪点背景

    仔细观察的话,页面背景并不是单纯的黑色,而是会有轻微的类似电视机 雪花 噪点效果,通过以下样式即可实现噪点效果。

    <div class="bg"></div>
    

    背景是一张噪点图片,设置背景时将 background-repeat 设置为 repeat 并添加通过translate 实现位移的动画实现噪点晃动效果。

    .bg {
      position: fixed;
      top: -50%;
      left: -50%;
      right: -50%;
      bottom: -50%;
       200%;
      height: 200vh;
      background: transparent url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAEAAAABAAgMAAADXB5lNAAAADFBMVEUvLy9eXl6AgICoqKhWH7o7AAAABHRSTlMSEhIS3WyPCwAAA1hJREFUOMsN0M3rDHEcwPH3d3y/4zcr67s1s3bIU62y8nBxcVCf79pZ4WBWsx6TVbvyEKUolJrxmBTj4SecVqE4OTjgIP6D5eC8DkouOJAj19fxhXJCWn811mk1Sp1q0J0q6AoNF7ZQ0uD+74CBj3otoUUEmJc0wqVEr2Ulatp1/6HYA9SGwfn+s6ftD8zsbic1idsPVrfcoQRYSrvbd7PdA7TY6cKcbfrwRXaJaqgTXSfDKd625S7XGB1YraJ0yuatOJmJvf5aqIwYINvBGIr+gZiDl80Qdoh3M1GTfuCzf1+yEetme3loJ3Hf6yijG5S9rRa7XI7Nzu1AYGF5Bd1cNeplTmN8yJpV8kYrpKEIAzXDgbBK2QhhTb37NP4P1aqRZ3ua6DVLb2AKjVpgBkbHie4QGFVqxDcpgL4tlTUMNKKgazpmWC+CkBBkTu59dpl+XikMg+U5izd/9z+KpxcFYvxxs01Vtho32XLZBNRmy8YWQBszOV6ES9r7cvQdshRbKVdfOrDKeyB+MeXsWvMmI95/Pdsp7J5MydZHR9MonithyhIllnSppjGaQRkb7vVyTaqNhLUsVI5I/HEDi3JYWdu+KEgsmkzJXGPZ97wQyqPREfp+vmAvzo3AfhF9HvZS1SiZL9H4pVgfhmofCltJ3wxq9/961Aaqq3HpzsFroqtPe9SVm3Ol5yd3f99TueB46l+9lB/drm4PxXs/4j4j5k6pAzS88njnDp72JijRYlYFRMaxfY8q20pWZjGLdKsCP2YoVYXl9RK1Kp7Xpx8MLYEe+gIWlUDwJNABR0AVAGQ4rfcCrci5YQYZonhi9ckLVrkTeCTeL5+0H7+Lw1baYjGu+6ddepc6qeLc8EhvL3dvf5Xi9maHyrGnCmFXXo7bk83O3C6FFYVDURtfLD4YVUpO011EfYvktpukxpKogevhPViJPC6tmWnOcxkaJYnwOw2zyoYKeAmKIlfpILLxBmOo3yLlkzh5+yTKmkvtrsc3oP8Tx7t8YTms2Be9a0TJNJ21Gb6k5mwY9Vn/P2vRSHu7tiZ2kx6mrMtCoqPG+9w3YWxOw5EZDcszz+tUQhZlq8j8Rw77ynqzi7XaV3kH8x62ScfWdhZpkgX3wWdZcibtbFASgOEfZmfZzbdc/O0AAAAASUVORK5CYII=') repeat 0 0;
      background-repeat: repeat;
      animation: bg-animation .2s infinite;
    }
    @keyframes bg-animation {
      0% { transform: translate(0,0) }
      10% { transform: translate(-5%,-5%) }
      // ...
      100% { transform: translate(5%,0) }
    }
    

    完整代码:https://github.com/dragonir/shengshengbuxi

    总结

    本文包含的知识点主要包括:

    • repeating-linear-gradient 条纹背景
    • clip-path 形状裁切
    • background-clip 设置元素的背景延伸
    • Window.getComputedStyle() 获取计算后元素的所有 CSS 属性的值
    • CSSStyleDeclaration.getPropertyValue() 获取请求的 CSS 属性的值

    想了解其他前端知识或 WEB 3D 开发技术相关知识,可阅读我往期文章。转载请注明原文地址和作者。如果觉得文章对你有帮助,不要忘了一键三连哦

    附录

    3D

    参考

    作者:dragonir 本文地址:https://www.cnblogs.com/dragonir/p/16265984.html

  • 相关阅读:
    request.getParameterMap 跟request.getParameter区别
    SQL语句中---删除表数据drop、truncate和delete的用法
    今日出现两个错误
    html和jsp的区别及优缺点
    怎么将 美国的日期格式改成中国的日期格式
    java web相关的面试题
    i++与++i的关系
    Oracle常见的语法,以及跟MySQL的区别
    DBA
    java基础之印象笔记
  • 原文地址:https://www.cnblogs.com/dragonir/p/16265984.html
Copyright © 2020-2023  润新知