首页 > 解决方案 > 是否可以使用 css3 变量作为 SASS mixin 的参数?

问题描述

我想知道是否可以在 sass 中的动画混合中调用 css 变量以具有基于动态动画颜色的效果。

我在 Sass 中尝试了很多关于插值的方法,但从未成功。没有动态颜色的 mixin 版本可以正常工作,但不能使用动态 css 变量。

所以我想知道这是否可能以及如何实现?

我正在使用 node-sass(版本:1.22.9)。

看法

<ion-button class="pulse pulse-danger"></ion-button>

SCSS


# Var
--ion-color-primary: #FFFFFF;
--ion-color-danger: #000000;

/**
 * Pulse Animation
 */
@mixin animation-pulse($duration, $color-name) {

    $name: animation-pulse-#{$color-name};

    @keyframes #{$name} {
        0% {
            -moz-box-shadow: 0 0 0 0 #{"rgba(--ion-color-#{$color-name}, 0.4)"};
            box-shadow: 0 0 0 0 #{"rgba(--ion-color-#{$color-name}, 0.4)"};
        }
        70% {
            -moz-box-shadow: 0 0 0 10px #{"rgba(--ion-color-#{$color-name}, 0)"};
            box-shadow: 0 0 0 10px #{"rgba(--ion-color-#{$color-name}, 0)"};
        }
        100% {
            -moz-box-shadow: 0 0 0 0 #{"rgba(--ion-color-#{$color-name}, 0)"};
            box-shadow: 0 0 0 0 #{"rgba(--ion-color-#{$color-name}, 0)"};
        }
    }

    @-webkit-keyframes #{$name} {
        0% {
            -webkit-box-shadow: 0 0 0 0 #{"rgba(--ion-color-#{$color-name}, 0.4)"};
        }
        70% {
            -webkit-box-shadow: 0 0 0 10px #{"rgba(--ion-color-#{$color-name}, 0)"};
        }
        100% {
            -webkit-box-shadow: 0 0 0 0 #{"rgba(--ion-color-#{$color-name}, 0)"};
        }
    }

    animation-name: $name;
    animation-duration: $duration;
    animation-iteration-count: infinite;
}

.pulse {

    &:hover {
        animation: none;
    }

    &.pulse-primary {

        background: var(--ion-color-primary);
        box-shadow: 0 0 0 rgba(var(--ion-color-primary), 0.4);

        @include animation-pulse(2s, primary);
    }

    &.pulse-danger {
        background: var(--ion-color-danger);
        box-shadow: 0 0 0 rgba(var(--ion-color-danger), 0.4);

        @include animation-pulse(2s, danger);
    }

}

实际结果未显示脉冲动画可能是由于未在 mixin 中正确设置 css var。

如果我在混合动画中用静态值替换脉冲颜色,则脉冲动画正在工作。

标签: csssass

解决方案


是的,您可以,但是,您有一些问题:

  1. 您缺少var()mixin 中的变量名称。
  2. 您不能rgba()在变量中使用十六进制值。将 CSS 变量与 rgba 一起使用以实现渐变透明度
  3. 您还需要将background按钮上的属性更改为rgbabackground: rgb(var(--ion-color-danger));

这是新的 SASS:

:root {
--ion-color-primary: 255,255,255;
--ion-color-danger: 0,0,0;
}

/**
 * Pulse Animation
 */
@mixin animation-pulse($duration, $color-name) {

    $name: animation-pulse-#{$color-name};

    @keyframes #{$name} {
        0% {
            -moz-box-shadow: 0 0 0 0 #{"rgba(var(--ion-color-#{$color-name}), 0.4)"};
            box-shadow: 0 0 0 0 #{"rgba(var(--ion-color-#{$color-name}), 0.4)"};
        }
        70% {
            -moz-box-shadow: 0 0 0 10px #{"rgba(var(--ion-color-#{$color-name}), 0)"};
            box-shadow: 0 0 0 10px #{"rgba(var(--ion-color-#{$color-name}), 0)"};
        }
        100% {
            -moz-box-shadow: 0 0 0 0 #{"rgba(var(--ion-color-#{$color-name}), 0)"};
            box-shadow: 0 0 0 0 #{"rgba(var(--ion-color-#{$color-name}), 0)"};
        }
    }

    @-webkit-keyframes #{$name} {
        0% {
            -webkit-box-shadow: 0 0 0 0 #{"rgba(var(--ion-color-#{$color-name}), 0.4)"};
        }
        70% {
            -webkit-box-shadow: 0 0 0 10px #{"rgba(var(--ion-color-#{$color-name}), 0)"};
        }
        100% {
            -webkit-box-shadow: 0 0 0 0 #{"rgba(var(--ion-color-#{$color-name}), 0)"};
        }
    }

    animation-name: $name;
    animation-duration: $duration;
    animation-iteration-count: infinite;
}

.pulse {

    &:hover {
        animation: none;
    }

    &.pulse-primary {

        background: rgb(var(--ion-color-primary));
        box-shadow: 0 0 0 rgba(var(--ion-color-primary), 0.4);

        @include animation-pulse(2s, primary);
    }

    &.pulse-danger {
        background: rgb(var(--ion-color-danger));
        box-shadow: 0 0 0 rgba(var(--ion-color-danger), 0.4);

        @include animation-pulse(2s, danger);
    }

}

这是编译后的代码,它可以工作:

:root {
  --ion-color-primary: 255, 255, 255;
  --ion-color-danger: 0, 0, 0;
}


/**
 * Pulse Animation
 */

.pulse:hover {
  animation: none;
}

.pulse.pulse-primary {
  background: rgb(var(--ion-color-primary));
  box-shadow: 0 0 0 rgba(var(--ion-color-primary), 0.4);
  animation-name: animation-pulse-primary;
  animation-duration: 2s;
  animation-iteration-count: infinite;
}

@keyframes animation-pulse-primary {
  0% {
    -moz-box-shadow: 0 0 0 0 rgba(var(--ion-color-primary), 0.4);
    box-shadow: 0 0 0 0 rgba(var(--ion-color-primary), 0.4);
  }
  70% {
    -moz-box-shadow: 0 0 0 10px rgba(var(--ion-color-primary), 0);
    box-shadow: 0 0 0 10px rgba(var(--ion-color-primary), 0);
  }
  100% {
    -moz-box-shadow: 0 0 0 0 rgba(var(--ion-color-primary), 0);
    box-shadow: 0 0 0 0 rgba(var(--ion-color-primary), 0);
  }
}

@-webkit-keyframes animation-pulse-primary {
  0% {
    -webkit-box-shadow: 0 0 0 0 rgba(var(--ion-color-primary), 0.4);
  }
  70% {
    -webkit-box-shadow: 0 0 0 10px rgba(var(--ion-color-primary), 0);
  }
  100% {
    -webkit-box-shadow: 0 0 0 0 rgba(var(--ion-color-primary), 0);
  }
}

.pulse.pulse-danger {
  background: rgb(var(--ion-color-danger));
  box-shadow: 0 0 0 rgba(var(--ion-color-danger), 0.4);
  animation-name: animation-pulse-danger;
  animation-duration: 2s;
  animation-iteration-count: infinite;
}

@keyframes animation-pulse-danger {
  0% {
    -moz-box-shadow: 0 0 0 0 rgba(var(--ion-color-danger), 0.4);
    box-shadow: 0 0 0 0 rgba(var(--ion-color-danger), 0.4);
  }
  70% {
    -moz-box-shadow: 0 0 0 10px rgba(var(--ion-color-danger), 0);
    box-shadow: 0 0 0 10px rgba(var(--ion-color-danger), 0);
  }
  100% {
    -moz-box-shadow: 0 0 0 0 rgba(var(--ion-color-danger), 0);
    box-shadow: 0 0 0 0 rgba(var(--ion-color-danger), 0);
  }
}

@-webkit-keyframes animation-pulse-danger {
  0% {
    -webkit-box-shadow: 0 0 0 0 rgba(var(--ion-color-danger), 0.4);
  }
  70% {
    -webkit-box-shadow: 0 0 0 10px rgba(var(--ion-color-danger), 0);
  }
  100% {
    -webkit-box-shadow: 0 0 0 0 rgba(var(--ion-color-danger), 0);
  }
}
<button class="pulse pulse-danger">test button big for visual</button>


推荐阅读