CSS @keyframesでアニメーション作って遊んでみた

# 対象読者
- アニメーションに興味ある人
- CSS @規則 keyframesに触れてみたいなっていう人
- ちょっとHTML/CSSを理解している人（初学者）

# 前置き

始めまして、マイスター・ギルドのおれさまちゃんです（ひどいネーミングと思われた方は[こちらの記事](https://note.com/oresamachan/n/ncaba53064cc9)を見てもらったら、ひょっとすると笑えるかもです）。

今回、初の技術ブログへの投稿となりますので、お手柔らかにお願いします。
一応、ガイドラインは見ました...

# では本題

今回、ちょっとアニメーションというものに興味が湧き（若干仕事でも引き合いがありまして・・・）、全然スキル領域の違うところへチャレンジしてみようかと思った次第で、題材的には、上の方で書いた通りCSS [@keyframes](https://developer.mozilla.org/ja/docs/Web/CSS/@keyframes)を使ってWebでアニメーションなるものを体験してみようかと思います。

# CSS @規則
あっとまーくきそく（アットルール）と呼ぶそうです。
＠（あっとまーく）から始まる宣言で動作を規定するものだそうです。
今回はそのなかで[@keyframes](https://developer.mozilla.org/ja/docs/Web/CSS/@keyframes)を利用してアニメーションを作成してみたいと思います。

>[@keyframes](https://developer.mozilla.org/ja/docs/Web/CSS/@keyframes)
>CSS アニメーションシーケンスの中間段階に関する指定を記述します。

だそうです。なるほど。
英語の意味をついつい考えてしまいがちなのですが、key + frames に分解したときに、アニメーションのフレーム群（frames）に対して鍵（key）となるポイントを示した感じなのかなと理解しました。


# とりあえず、書き方の基本

まずは簡単な記法の紹介。

```css:sample.css
.className {
  /*CSS記述*/
  animation: rule_hogehoge 10s infinite;
}

@keyframes rule_hogehoge {
  from {
    /*CSSで最初の状態を示す*/
  }
  to {
    /*CSSで最後の状態を示す*/
  }
}
```

何かの要素（セレクタ）に[animationプロパティ](https://developer.mozilla.org/ja/docs/Web/CSS/animation)（CSS記述）を足して、その中（値、ここだとrule_hogehoge）のキーワードを[@keyframesから始まる規則](https://developer.mozilla.org/ja/docs/Web/CSS/@keyframes)でアニメーションのルールを書いていく。
この場合だと、rule_hogehogeで定義したアニメーションを10秒に渡って継続的に繰り返すのですが、fromに最初（0秒）の状態、toには10秒後の状態をcssで記述してあげると、その間のフレーム（アニメーション的な意味での）をいい感じに補完してくれます。

## 例1：
div要素の幅を10pxから段々幅広にしていくアニメーション。
![kf_step1.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2149410/f85adbab-af9b-a8f9-a5df-f29d62a0b3b5.gif)

```index.html
<!DOCTYPE html>
<html>
<head>
    <meta charset='utf-8'>
    <link rel='stylesheet' type='text/css' media='screen' href='step1.css'>
</head>
<body>
    step1:
    <div id="animation_container">@keyframes</div>
</body>
</html>
```

```step1.css

div#animation_container {
    margin: 10px 10px;
    text-align: right;
    color: white;
    background-color: blueviolet;
    animation: anime_step1 5s infinite;/*kf_step1アニメーションを5秒の尺で表現、無限に繰り返し*/
}

@keyframes anime_step1 {
    from {
        width: 90px;
    }
    to {
        width: 100%;
    }
}
```

## 例2:
参考にしたサイトの最初の説明ではfrom、toが基本のようですが、%指定を使って、細かく要所要所の状態を指定することもできるようです（こっちの方がより実用的なイメージ。かなり細かく指定できるので）。

```step2.css

@keyframes anime_step2 {
    /*（見落としがちかも）0%は省略可能*/
    20% {
        width: 10px;
    }
    40% {
        width: 30%;
    }
    60% {
        width: 60%;
        height: 50px;
    }
    80% {
        width: 65%;
        height: 150px;
    }
    100% {
        width: 90%;
        height: 200px;
    }
}
```

![kf_step2.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2149410/ec539b26-9149-774b-d955-6d1772d52438.gif)

例ではwidth、heightを利用しましたが、top、leftなどのプロパティでもアニメーションさせることができます。
その他特殊な指定方法などをもう少し書いていきます。

# transform プロパティを利用してさらに複雑なアニメーションを作る

とりあえずtransformプロパティでめぼしいものを使って、ぐりぐりやってみた。

## 例3:

```step3.css

/* step3 */
@keyframes anime_hige {
    25%{  transform: rotate(10deg);  }
    50%{  transform: rotate(50deg);  }
    75%{  transform: rotate(-30deg); }
    100%{ transform: rotate(0deg);   }
}
@keyframes anime_meister {
    80%{  transform: scaleX(120%) scaleY(140%); }
    100%{ transform: scaleX(100%) scaleY(100%); }
}
@keyframes anime_char_g {
    50%{  transform:rotate3d(1,0,0,180deg); }
    100%{ transform:rotate3d(1,0,0,0deg); }
}
@keyframes anime_char_u {
    50%{  transform:rotate3d(1,0,0,180deg); }
    100%{ transform:rotate3d(1,0,0,0deg); }
}
@keyframes anime_char_i {
    50%{  transform:rotate3d(1,0,0,180deg); }
    100%{ transform:rotate3d(1,0,0,0deg); }
}
@keyframes anime_char_l {
    50%{  transform:rotate3d(1,0,0,180deg); }
    100%{ transform:rotate3d(1,0,0,0deg); }
}
@keyframes anime_char_d {
    50%{  transform:rotate3d(1,0,0,180deg); }
    100%{ transform:rotate3d(1,0,0,0deg); }
}

```

![kf_step3.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2149410/146c36b9-0c65-d907-037f-d162150321a3.gif)

# アニメーション素材を準備する

よくあるHTMLのspan、div要素なんかをただただ動かしてもあまり面白味はないので、ちょっとキャラクターを準備しました。
（某社のキャラクターデザインのオマージュです。すいません。一番、ここに時間がかかったかも...div要素とcssを駆使）

![MG_kanazuti_image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2149410/da5017e8-5c14-d7a8-3f9e-ff30aa03f8ee.png)




# 「こいつ、動くぞ」（言ってみたかった）

![kf_step5.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2149410/ad75fdcc-d5a2-779e-c35b-e8cba3a24527.gif)


ソースはこんな感じになりました。ちょっと長くて見づらい点はご了承ください。

```step4.css

/* step4 */
/*animation parts*/
/*右手アニメーション*/
@keyframes anime_r_hand{
    0%{  transform: rotate(-40deg);}
    50%{ transform: rotate(40deg);}
    70%{ transform: rotate(-40deg);}
    72%{ transform: rotate(40deg);}
    74%{ transform: rotate(-40deg);}
    76%{ transform: rotate(40deg);}
    100%{transform: rotate(-40deg);}
}
/*左手アニメーション*/
@keyframes anime_l_hand{
    0%{  transform: rotate(40deg);}
    50%{ transform: rotate(-40deg);}
    70%{ transform: rotate(40deg);}
    72%{ transform: rotate(-40deg);}
    74%{ transform: rotate(40deg);}
    76%{ transform: rotate(-40deg);}
    100%{transform: rotate(40deg);}
}
/*右足アニメーション*/
@keyframes anime_r_foot{
    0%{  transform: rotate(-40deg);
         transform-origin:right;}
    50%{ transform: rotate(40deg);
         transform-origin:right;}
    100%{transform: rotate(-40deg);
         transform-origin:right;}
}
/*左足アニメーション*/
@keyframes anime_l_foot{
    0%{  transform: rotate(-40deg);
         transform-origin:left;}
    50%{ transform: rotate(40deg);
         transform-origin:left;}
    100%{transform: rotate(-40deg);
         transform-origin:left;}
}
/*目アニメーション*/
@keyframes anime_eyes{
    63%{background-color: #000050;}
    64%{background-color: crimson;
        filter: drop-shadow(1px -4px 3px crimson);}
    100%{background-color: fuchsia;}
}
/*体アニメーション*/
@keyframes anime_kanazuti_body{
    0%{  top: -100px; left: 400px;
         transform:scale(0.2);}
    60%{ top: 150px; left: 100px;
         transform:scale(1.0);}
    64%{ top: 165px; left: 65px;
         transform:scaleX(1.2);}
    70%{ top: 70px; left: 30px;
         transform:scaleX(1.0);}
    80%{ top: 50px;  left: 10px;
         transform:scaleX(1.0);}
    88%{ top: 150px; left: -30px;}
    100%{top: 120px; left: -500px;}
}

```

# まとめ

いろいろ遊んでみましたが、keyframesのタイミングだけ理解できてしまえばあとはCSSの表現だけなので、結構簡単にアニメーションを作ることができました。
他のサイトを見ているとtransitionなんかとの比較も出ていますが、またそれはどこかで。

# 参考

https://developer.mozilla.org/ja/docs/Web/CSS/@keyframes