doors doors
chart.js

jsで動く!アニメーショングラフ

  • HOME
  • TRY
  • chart.jsでアニメーションするグラフを作ってみた

chart.jsでアニメーションするグラフを作ってみた

chart.js

グラフ画像をただ置いておいても、円グラフはただの丸、棒グラフもただの棒の並びのように見えてしまい、なかなか注目されないものです。

そこでグラフを動かすchart.jsで、グラフをニョキニョキっと動かし、視認性UPに繋がるようにしてみました。

しかし単純にサンプルコードから引っ張って来ても動かなかったり、参考ページを見て追加したことなど、カスタマイズした項目もありますので、合わせてご紹介したいと思います。

公式サイトからDL

公式サイトはこちら

上記からGit hubへアクセスして、chart.jsをDLし、任意のjsディレクトリにUPしておきます。

コードを記述

HTMLファイルのscriptタグまたは外部jsファイルの中身に、以下を記述します。

デモコードよりもさらに記述を追加していますが後に紹介します。

//スクロールしたとき、画面中央で発火して動くようにする
var chartEl1 = document.getElementById("circleChart");
var chartEl2 = document.getElementById("barChart");
var chartFlag1 = false;             
var chartFlag2 = false;             
                             
// 1つ目のグラフ              
var chartFunc1 = function() {               
var ctx = chartEl1.getContext('2d');                
chart = new Chart(ctx, {                
    type: 'pie',            
                
    options: {          
        maintainAspectRatio: false, //アスペクト比維持解除        
        tooltips: [{        
        enabled: false      
        }]      
    },          
                
    layout: { //レイアウト           
        padding: { //余白設定       
            left: 0,    
            right: 0,   
            top: 0, 
            bottom: 0   
        }       
    },          
                
    data: {         
        datasets: [{        
            label: 'label', 
            data: [3, 18, 6, 10, 12],   
            backgroundColor: ["#000","#333","#666","#999","#aaa"]   
        }]      
    }           
    });         
};              
                
//------------------グラフ2の設定 中略------------------              
                
//スクロール処理
var graphAnim = function() {                
    var wy = window.pageYOffset,            
    wb = wy + window.innerHeight,         

    chartElPos1 = wy + chartEl1.getBoundingClientRect().top + ( screen.height / 2 ),            
    chartElPos2 = wy + chartEl2.getBoundingClientRect().top + ( screen.height / 2 );          
        
    if ( wb > chartElPos1 && chartFlag1 == false ) {            
        chartFunc1();       
        chartFlag1 = true;      
    }           
                
    if ( wb > chartElPos2 && chartFlag2 == false ) {            
        chartFunc2();       
        chartFlag2 = true;      
    }           
};              
                
window.addEventListener('load', graphAnim); 
window.addEventListener('scroll', graphAnim);

上記は2つ目のグラフ設定を省略しています。
設定についての詳細は以下のページにて紹介されていましたので、そちらをぜひ参考にしてみてください。

画面中央で発火させるようにする

公式のデモコードをそのまま引用するだけでは、ページロード時に読み込まれてしまい、ファーストビュー外にアニメーションをつけたグラフがあってもそのアニメーションを確認することはできません。
そこでスクロールをして画面中央あたりで発火、アニメーションが始まるようにしています。

//スクロールしたとき、画面中央で発火して動くようにする
var chartEl1 = document.getElementById("circleChart");
var chartEl2 = document.getElementById("barChart");
var chartFlag1 = false;             
var chartFlag2 = false;             
                                       
//------------------グラフの設定 中略------------------              
                
//以下からスクロール処理              
var graphAnim = function() {                
    var wy = window.pageYOffset,            
    wb = wy + window.innerHeight,       
                          
    chartElPos1 = wy + chartEl1.getBoundingClientRect().top + ( screen.height / 2 ),            
    chartElPos2 = wy + chartEl2.getBoundingClientRect().top + ( screen.height / 2 ); //ブラウザ中央に来るくらいで出て来るようにする           
   
    if ( wb > chartElPos1 && chartFlag1 == false ) {            
        chartFunc1();       
        chartFlag1 = true;      
    }           
                
    if ( wb > chartElPos2 && chartFlag2 == false ) {            
        chartFunc2();       
        chartFlag2 = true;      
    }           
};              
                
window.addEventListener('load', graphAnim);           
window.addEventListener('scroll', graphAnim);

このコードはこちらを参考にさせていただきました。ありがとうございます。

    chartElPos1 = wy + chartEl1.getBoundingClientRect().top + ( screen.height / 2 ),            
    chartElPos2 = wy + chartEl2.getBoundingClientRect().top + ( screen.height / 2 ); //ブラウザ中央に来るくらいで出て来るようにする           

”( screen.height / 2 )” については、画面中央を想定しての計算式になります。 適宜変更してみてください。

スマホ対応

スマホではグラフ部分だけが表示されるようにします。
何も設定しないままだと、たとえ円グラフであっても左右に余白ができてしまい、グラフそのものが縮んでしまいます。
スマホだけではなく、親要素の幅に合わせたい時などにも便利ですね。

    options: {          
        maintainAspectRatio: false, //アスペクト比維持解除        
        tooltips: [{        
        enabled: false      
        }]      
    },          
                
    layout: { //レイアウト           
        padding: { //余白設定       
            left: 0,    
            right: 0,   
            top: 0, 
            bottom: 0   
        }       
    },  

まずmaintainAspectRatioをfalseにしてアスペクト比維持を解除します。 また、余白の設定も全て0にします。

HTML記述の注意点

私はここで一度ハマってしまったのですが、HTMLでは親要素に特定の記述をする必要があります。

<div class="wrap">
  <section> <!--なるべく親をつけて内包する-->
    <canvas id="circleChart"></canvas>
  </section>
  <section> <!--なるべく親をつけて内包する-->
    <canvas id="barChart"></canvas>
  </section>
</div> 

テスト段階の時、何にも挟まずにcanvasを直置きしていましたが、高さを設定しない限り全く動きませんでした。
なるべく上記のようにsectionタグなどで挟んでください。

cssの注意点

上記で説明したとおり、chart.jsは親要素に高さの指定が無いと動来ません。
そこで親要素に内包し、その親要素に高さを指定します。

以下略していますが必要な箇所だけ抜粋します。

body, html {    
/*height: 100%*/  /*親要素無しに直置きする場合はbody,htmlに高さ指定*/  
}   
    
.wrap { 
    width : 100%;
}   
    
section {   
    width:80vw;
    height:50vh; /*高さ指定をする*/
    margin : 100px auto 800px;
    position : relative;
}

もし表示されずに困っているようでしたら、上記の通り、親要素に高さ指定をしてみてください。

関連記事

aタグでリンクを繋げる際に気をつけたい事

aタグで外部へリンクを繋げる時、単純に<a href=”〜〜〜〜” target=”_blank”>リンクを繋げる</...

Brackets|サポート終了

Brackets|突然、告げられるサポート終了 参りました・・・2021年9月をもってBracketsサポート終了です。確かにAdobeとしては、Bracket...

Dreamweaver|ライブラリのリンク

状況 Dreamweaverのライブラリを使用する場合で、トップページ(index.html)のリンクは <a href="../">トップページ&...

WEB:企業サイト、PRサイト、ランディングページ、バナー制作やCMS構築、モーショングラフィックス、VP、動画制作、パンフレット、ポスター、チラシ、DMなど制作から印刷・納品まで。 お気軽にお問い合わせください。

Illustrator|3Dとマテリアル

イラストレータの3Dが復活! しかもパワーアップして戻ってきました!  バージョ...

Dreamweaver|ライブラリのリンク

状況 Dreamweaverのライブラリを使用する場合で、トップページ(inde...

Brackets|サポート終了からその後・・・

Brackets|サポート終了からその後 結論からお伝えすると、今は「Brack...

Brackets|サポート終了

Brackets|突然、告げられるサポート終了 参りました・・・2021年9月を...