10

あまりにも似ている 8 つの異なる CSS3 アニメーションが必要なので、LESS を使用しました。以下は、@name 変数の小さな不具合が 1 つありますが、完全に機能するコードです。

.animation_top (@name, @pxFrom, @pxTo) {
    @-moz-keyframes @name {
        0% {
            top: @pxFrom;
            opacity: 0;
        }
        100% {
            top: @pxTo;
            opacity: 1;
        }
    }

    @-webkit-keyframes @name {
        0% {
            top: @pxFrom;
            opacity: 0;
        }
        100% {
            top: @pxTo;
            opacity: 1;
        }
    }

    @-ms-keyframes @name {
        0% {
            top: @pxFrom;
            opacity: 0;
        }
        100% {
            top: @pxTo;
            opacity: 1;
        }
    }
}

CSS キーフレームは @ 記号で始まるため、LESS は @name の変数を単純に無視します。キーフレームの @ 記号をエスケープする方法、または LESS に @name を適切にレンダリングさせる方法はありますか?

4

3 に答える 3

13

EDIT
セレクター のサポートは、(~"@{varname}")LESS 1.4.0 で削除されます。
元のソリューションを機能させるには、一時変数を導入し、セレクタ補間(LESS 1.3.1 の新機能) を利用するだけです。
前の例では、これは次のようになります。

 @tmp: ~"@{varname}"
 @{tmp} { ... }

以下の説明では、簡潔であるため、古いセレクターを使用しています。前に示したように、古いメソッドを新しいメソッドに置き換えるのは簡単です。
私たちの多くはやみくもにコードをコピーして貼り付けているので、コード例を更新しました。

予想される構文は (vendorprefixed)(~"@keyframes @{name}") { ... }です。ただし、出力は正しくありません (セレクターは にマージされ@keyframes name 0% { ... } @keyframes name 100% {}ます)。これは、 のツリー構文がより少ないソース コード@keyframesで例外として定義されているためです。

私の狡猾な mixin の背後にあるアイデアは、セレクターを介して中括弧を追加することです。

  • 初期セレクターは になります(~"@keyframes @{name}{") { ... }
    これは次のようにレンダリングされます。@keyframes name {{ ... }
  • 見栄えが悪いので{{、改行を入れます。改行を直接エスケープできなかったので、変数を作成することにしました@newline: `"\n"`;。Lessは、バックティック間のすべてを JavaScript として解析するため、結果の値は改行文字になります。「セレクター」が有効である必要があるため{ ... }、アニメーションの最初のステップ0%.
  • 中括弧が一致しません。これを修正するには、最後に で始まるダミー セレクターを追加し(~"} dummy") { .. }ます。役に立たないセレクターが追加されているため、これは醜いです。
    しかし、待ってください。ベンダー固有のプレフィックスが順次追加されることはすでにわかっています。したがって、最後の最初のセレクターを とします(~"@{pre}@@{vendor}keyframes @{name} {@{newline}0%")。最初のキーフレーム以降のすべてのキーフレーム ブロックに対応
    @{pre}する必要があります。"}@{newline}"
  • これで、最後のブロックを除くすべてのブロックの閉じ中括弧を処理しました。キーフレームを使用するために明らかにキーフレームを定義するため、無駄なダミーセレクターを使用する必要はありません。animation-nameそうするプロパティです。これを実装するために保護されたミックスインを使用しています。

このソリューションは、最初はややぎこちなく見えるかもしれませんが、非常に簡潔です。

@newline: `"\n"`; // Newline
.animation_top(@selector, @name, @pxFrom, @pxTo) {
    .Keyframe(@pre, @post, @vendor) {
        @keyframe: ~"@{pre}@@{vendor}keyframes @{name} {@{newline}0%";
        @{keyframe} {
            top: @pxFrom;  
            opacity: 0;  
        }    
        100%  { 
            top: @pxTo;
            opacity: 1;
        }    
        .Local(){}
        .Local() when (@post=1) {
            @local: ~"}@{newline}@{selector}";
            @{local} {
                -moz-animation: @name;
                -webkit-animation: @name;
                -o-animation: @name;
                -ms-animation: @name;
                animation: @name;
            } 
        }    
        .Local;
    } 
    .Keyframe(""            , 0,    "-moz-");
    .Keyframe(~"}@{newline}", 0, "-webkit-");
    .Keyframe(~"}@{newline}", 0,      "-o-");
    .Keyframe(~"}@{newline}", 0,     "-ms-");
    .Keyframe(~"}@{newline}", 1,         ""); // <-- Vendorless w3
} 
.animation_top("#test", hey, 10px, 100px);

としてレンダリングされます (キーフレーム内のインデントが 1 つずれていることに注意してください。手動で追加された中括弧により、Less は別のブロック内にいることを認識していないため、これは予期されたものです)。

以下の結果は、LESS バージョン 1.3.3 および 1.4.0-b1 を使用して確認されています。

$ lessc --version
lessc 1.3.3 (LESS Compiler) [JavaScript]
$ lessc so
@-moz-keyframes hey {
0% {
  top: 10px;
  opacity: 0;
}
100% {
  top: 100px;
  opacity: 1;
}
}
@-webkit-keyframes hey {
0% {
  top: 10px;
  opacity: 0;
}
100% {
  top: 100px;
  opacity: 1;
}
}
@-o-keyframes hey {
0% {
  top: 10px;
  opacity: 0;
}
100% {
  top: 100px;
  opacity: 1;
}
}
@-ms-keyframes hey {
0% {
  top: 10px;
  opacity: 0;
}
100% {
  top: 100px;
  opacity: 1;
}
}
@keyframes hey {
0% {
  top: 10px;
  opacity: 0;
}
100% {
  top: 100px;
  opacity: 1;
}
}
#test {
  -moz-animation: hey;
  -webkit-animation: hey;
  -o-animation: hey;
  -ms-animation: hey;
  animation: hey;
}

最終的な注意事項:

  • 有効な CSS を生成する最短のダミーは/**/. 例: (~"..") {/**/}-> .. {/**/}.
于 2012-06-14T07:32:42.167 に答える
0

おそらくこれはあなたが望むものですか?あなたが定義するなら@name: "ANIM_NAME";、私はこれが方法だと思います:

@-moz-keyframes @{name} {
...
...
}
于 2012-02-06T20:38:39.217 に答える