「Snap.svg」を使ってSVGをアニメーションしてみた

技術情報
本ページは広告およびアフィリエイトプログラムによる収益を得ています。

Snap.svg – Home

JavaScriptでのSVGのアニメーションを楽にしてくれる「Snap.svg」というライブラリを知り、気になったので使ってみることにしました。

「Snap.svg」を導入する

トップページから「Snap.svg」をダウンロードして、「dist」フォルダにある「snap.svg-min.js」を使用します。

Downloadから「Snap.svg」をダウンロード
Downloadから「Snap.svg」をダウンロード

解凍して「dist」フォルダを開きます。

解凍して「dist」フォルダを開く

圧縮済みの「snap.svg-min.js」を使用します。

「snap.svg-min.js」を使用
「snap.svg-min.js」を使用

適当な名称のフォルダを作成し、「snap.svg-min.js」を入れて下記のような感じで読み込みます。

<script type="text/javascript" src="./snap.svg-min.js"></script>

「Snap.svg」を使ってアニメーションをする

カメラのsvg画像をボタンをクリックした時にボタンとシャッターを変化させて元に戻すアニメーションを実装します。

カメラのsvg画像をアニメーション

svg画像は「icooon-mono」を利用しています。

サンプル

スクリプト

全体のスクリプトは下記にようになります。

window.onload = function() {

    // ボタンアニメーション前のパス
    var pathBtnStart = 'M 290.864 38.648 H 435.068 V 93.314 H 290.864 V 38.648 Z';
    // ボタンアニメーション後のパス
    var pathBtnEnd = 'M 290.864 68.648 H 435.068 V 93.314 H 290.864 V 38.648 Z';

   // シャッターアニメーション前のパス
    var pathShutterStart = 'M256.001,226.93c-35.532,0-64.438,28.904-64.438,64.436c0,35.53,28.906,64.434,64.438,64.434 c35.529,0,64.434-28.904,64.434-64.434C320.435,255.834,291.53,226.93,256.001,226.93z';
    // シャッターアニメーション後のパス
    var pathShutterEnd = 'M 255.228 281.429 L 191.563 291.366 L 256.001 304.393 L 320.435 291.366 L 255.228 281.429 Z';

    var duration = 2; // 時間
    var easing = mina.easein; // 動き

    var button = Snap('#button'); // ボタンを取得
    var shutter = Snap('#shutter'); // シャッターを取得

    var isButton = true; // 条件用

    button.click(function(){

      if (isButton) {

        button.animate({path: pathBtnEnd}, duration, easing);
        shutter.animate({path: pathShutterEnd}, duration, easing);

        setTimeout(function(){
          button.animate({path: pathBtnStart}, duration, easing);
          shutter.animate({path: pathShutterStart}, duration, easing);
        }, 400);

      } else {

        button.animate({path: pathBtnStart}, duration, easing);
        shutter.animate({path: pathShutterStart}, duration, easing);

      }

    });

}

ボタンとシャッターのアニメーションの前後のパスを変数にいれます。後のパスは事前に作成しておく必要があります。「Snap.svg」はanimateでアニメーションを行います。svgの作成や編集はChrome拡張の「Boxy SVG」が手軽でお勧めです。

// ボタンアニメーション前のパス
var pathBtnStart = 'M 290.864 38.648 H 435.068 V 93.314 H 290.864 V 38.648 Z';
// ボタンアニメーション後のパス
var pathBtnEnd = 'M 290.864 68.648 H 435.068 V 93.314 H 290.864 V 38.648 Z';

// シャッターアニメーション前のパス
var pathShutterStart = 'M256.001,226.93c-35.532,0-64.438,28.904-64.438,64.436c0,35.53,28.906,64.434,64.438,64.434 c35.529,0,64.434-28.904,64.434-64.434C320.435,255.834,291.53,226.93,256.001,226.93z';
// シャッターアニメーション後のパス
var pathShutterEnd = 'M 255.228 281.429 L 191.563 291.366 L 256.001 304.393 L 320.435 291.366 L 255.228 281.429 Z';

アニメーションにかかる時間と動きを設定します。

var duration = 2; // 時間
var easing = mina.easein; // 動き

アニメーションを用に記述するボタンとシャッターのidを取得します。条件用の変数の「isButton」を作成します。

var button = Snap('#button'); // ボタンを取得
var shutter = Snap('#shutter'); // シャッターを取得

var isButton = true; // 条件用

ボタンがクリックされた時にボタンとシャッターのパスを取得してアニメーションを行っています。

button.click(function(){

  if (isButton) {

    button.animate({path: pathBtnEnd}, duration, easing);
    shutter.animate({path: pathShutterEnd}, duration, easing);

    setTimeout(function(){
      button.animate({path: pathBtnStart}, duration, easing);
      shutter.animate({path: pathShutterStart}, duration, easing);
    }, 400);

  } else {

    button.animate({path: pathBtnStart}, duration, easing);
    shutter.animate({path: pathShutterStart}, duration, easing);

  }

});

「isButton」の時にボタンとシャッターの変更されたパスを表示しています。pathで各パスの状態を取得、durationはかかる時間、easingはmina.easeinとなっています。setTimeoutで変更される前の通常のボタンとシャッターの表示に戻しています。

button.animate({path: pathBtnEnd}, duration, easing);
shutter.animate({path: pathShutterEnd}, duration, easing);

setTimeout(function(){
  button.animate({path: pathBtnStart}, duration, easing);
  shutter.animate({path: pathShutterStart}, duration, easing);
}, 400);

「else」で「isButton」以外の時に通常のボタンとシャッターを表示しています。

button.animate({path: pathBtnStart}, duration, easing);
shutter.animate({path: pathShutterStart}, duration, easing);

css

fillでsvgのカラー、cursorでボタン部分のパスに対してアイコンをポインターに変えています。

.st0 {
  fill: #4B4B4B;
}

.btn {
  cursor: pointer;
}

svg

svgは下記のようになっています。

<svg style="width: 256px; height: 256px" viewBox="0 0 512 512" xmlns="http://www.w3.org/2000/svg">
  <path id="button" class="st0 btn" d="M 290.864 38.648 H 435.068 V 93.314 H 290.864 V 38.648 Z"/>
  <path id="shutter" class="st0" d="M256.001,226.93c-35.532,0-64.438,28.904-64.438,64.436c0,35.53,28.906,64.434,64.438,64.434 c35.529,0,64.434-28.904,64.434-64.434C320.435,255.834,291.53,226.93,256.001,226.93z"/>
  <path class="st0" d="M440.599,114.603h-20.197H276.198H71.401C32.129,114.603,0,146.732,0,186.006v215.946
c0,39.27,32.129,71.401,71.401,71.401h369.198c39.272,0,71.401-32.131,71.401-71.401V186.006 C512,146.732,479.871,114.603,440.599,114.603z M88.817,241.732c-20.199,0-36.572-16.375-36.572-36.571
c0-20.199,16.373-36.574,36.572-36.574c20.197,0,36.57,16.375,36.57,36.574C125.387,225.357,109.014,241.732,88.817,241.732z
M256.001,392.374c-55.698,0-101.008-45.313-101.008-101.008s45.311-101.008,101.008-101.008 c55.694,0,101.006,45.312,101.006,101.008S311.695,392.374,256.001,392.374z"/>
</svg>

ボタンとシャッター部分にidを記述して、アニメーションに利用しています。

<path id="button" class="st0 btn" d="M 290.864 38.648 H 435.068 V 93.314 H 290.864 V 38.648 Z"/>
<path id="shutter" class="st0" d="M256.001,226.93c-35.532,0-64.438,28.904-64.438,64.436c0,35.53,28.906,64.434,64.438,64.434 c35.529,0,64.434-28.904,64.434-64.434C320.435,255.834,291.53,226.93,256.001,226.93z"/>

全体

サンプルページの全体となります。

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Snap.SVG</title>
<meta name="viewport" content="width=device-width,initial-scale=1" />
<script type="text/javascript" src="./snap.svg-min.js"></script>

<script>
window.onload = function() {

    // ボタンアニメーション前のパス
    var pathBtnStart = 'M 290.864 38.648 H 435.068 V 93.314 H 290.864 V 38.648 Z';
    // ボタンアニメーション後のパス
    var pathBtnEnd = 'M 290.864 68.648 H 435.068 V 93.314 H 290.864 V 38.648 Z';

   // シャッターアニメーション前のパス
    var pathShutterStart = 'M256.001,226.93c-35.532,0-64.438,28.904-64.438,64.436c0,35.53,28.906,64.434,64.438,64.434 c35.529,0,64.434-28.904,64.434-64.434C320.435,255.834,291.53,226.93,256.001,226.93z';
    // シャッターアニメーション後のパス
    var pathShutterEnd = 'M 255.228 281.429 L 191.563 291.366 L 256.001 304.393 L 320.435 291.366 L 255.228 281.429 Z';

    var duration = 2; // 時間
    var easing = mina.easein; // 動き

    var button = Snap('#button'); // ボタンを取得
    var shutter = Snap('#shutter'); // シャッターを取得

    var isButton = true; // 条件用

    button.click(function(){

      if (isButton) {

        button.animate({path: pathBtnEnd}, duration, easing);
        shutter.animate({path: pathShutterEnd}, duration, easing);

        setTimeout(function(){
          button.animate({path: pathBtnStart}, duration, easing);
          shutter.animate({path: pathShutterStart}, duration, easing);
        }, 400);

      } else {

        button.animate({path: pathBtnStart}, duration, easing);
        shutter.animate({path: pathShutterStart}, duration, easing);

      }

    });

}
</script>

<style type="text/css">
.st0 {
  fill: #4B4B4B;
}

.btn {
  cursor: pointer;
}
</style>

</head>
<body>

  <svg style="width: 256px; height: 256px" viewBox="0 0 512 512" xmlns="http://www.w3.org/2000/svg">
    <path id="button" class="st0 btn" d="M 290.864 38.648 H 435.068 V 93.314 H 290.864 V 38.648 Z"/>
    <path id="shutter" class="st0" d="M256.001,226.93c-35.532,0-64.438,28.904-64.438,64.436c0,35.53,28.906,64.434,64.438,64.434 c35.529,0,64.434-28.904,64.434-64.434C320.435,255.834,291.53,226.93,256.001,226.93z"/>
    <path class="st0" d="M440.599,114.603h-20.197H276.198H71.401C32.129,114.603,0,146.732,0,186.006v215.946
    c0,39.27,32.129,71.401,71.401,71.401h369.198c39.272,0,71.401-32.131,71.401-71.401V186.006 C512,146.732,479.871,114.603,440.599,114.603z M88.817,241.732c-20.199,0-36.572-16.375-36.572-36.571
    c0-20.199,16.373-36.574,36.572-36.574c20.197,0,36.57,16.375,36.57,36.574C125.387,225.357,109.014,241.732,88.817,241.732z
    M256.001,392.374c-55.698,0-101.008-45.313-101.008-101.008s45.311-101.008,101.008-101.008 c55.694,0,101.006,45.312,101.006,101.008S311.695,392.374,256.001,392.374z"/>
  </svg>

</body>
</html>

まとめ

  • 「snap.svg-min.js」を読み込む。
  • svgの前と変更後のパスを用意する。
  • 各pathを変数に入れてanimateでアニメーションを行う。

「Snap.svg」は噂通りjQueryのような感じで手軽に使えるライブラリだと思います。気になった方は利用を検討してみてはいかがでしょうか。

スポンサーリンク
技術情報
スポンサーリンク
シェアする
ボヘミアンをフォローする
この記事が気に入ったら
フォローしよう
最新情報をお届けします。
スポンサーリンク

コメント