Google Chart Tools - グラフと表の連携

今回は Google Chart Tools のグラフと表との連携です。
この表との連携や次回説明するフィルタリングが比較的簡単にかけることが Google Chart Tools の大きな利点の一つだと思います。

表とグラフでのデータの共有

連携の第一歩として同じデータで表とグラフを作成します。
<script type="text/javascript" src="https://www.google.com/jsapi"></script>
<script type="text/javascript">

  google.load('visualization', '1', {packages:['corechart', 'table']});
  google.setOnLoadCallback(
      function() {
          // データ定義
           var data = new google.visualization.arrayToDataTable([
               ['名前', '給料'],
               ['Mike',  10000],
               ['Jim',   8000 ],
               ['Alice', 12500],
               ['Bob',   7000 ]
           ]);
   
           // テーブルの作成
           var formatter = new google.visualization.NumberFormat(
               {pattern: '$#,###'});
           formatter.format(data, 1);
   
           var table = new google.visualization.Table(
               document.getElementById('gct_combo_sample1_table'));
           table.draw(data, {showRowNumber: true});
   
   
           // グラフの作成
           var chart_option = {hAxis:{format:'$#,###'}};
           var chart = new google.visualization.BarChart(
               document.getElementById('gct_combo_sample1_chart'));
           chart.draw(data, chart_option);
       }
   );

</script>
<table>
  <tr><td>
        <div id="gct_combo_sample1_table" style="width:150pt;" ></div>
    </td><td>
        <div id="gct_combo_sample1_chart" style="width:250pt; height:120pt;" ></div>
  </td></tr>
</table>
サンプルでは一つのデータから表とグラフを作成しています。

注意点としては、パッケージはグラフ用の "corechart""table" を両方をロードしています。

また、 NumberFormat をデータに適用していますが、 テーブルの値にしか影響はありません。 グラフの表示には別途 format オプションを使っています。

DataView による表の特定列とグラフとのデータ共有

表とグラフのデータを共有する際、テーブル全体ではなく、 テーブル内の特定の列のみ利用したい場合があります。
こういう時には DataView を使用します。

DataView は DataTable を渡して生成し、 setColumns() メソッドで利用したい列を指定します。
DataView::setColumns(列番号の配列)
js_gct_dataview.png
この DataView のオブジェクトを指定された列を抜き出した DataTable として使うことができます。
// データ定義
var data = new google.visualization.arrayToDataTable([
    ['名前', '給料', 'フルタイム', '入社年度'],
    ['Mike',  10000, true,         2000],
    ['Jim',   8000,  false,        2002],
    ['Alice', 12500, true,         1998],
    ['Bob',   7000,  true,         2001]
]);


// テーブルの作成
var formatter = new google.visualization.NumberFormat(
    {pattern: '$#,###'});
formatter.format(data, 1);
var formatter_year = new google.visualization.NumberFormat(
    {pattern: '#### 年'});
formatter_year.format(data, 3);

var table = new google.visualization.Table(
    document.getElementById('gct_combo_sample2_table'));
table.draw(data, {showRowNumber: true});


// DataView の作成
var vdata = new google.visualization.DataView(data);
vdata.setColumns([0, 1]);


// グラフの作成
var chart_option = {hAxis:{format:'$#,###'}};
var chart = new google.visualization.BarChart(
    document.getElementById('gct_combo_sample2_chart'));
chart.draw(vdata, chart_option);
以前紹介したグラフ作成を簡易化する ChartWrapper を使うと、 DataView の作成を省略して記述することもできます。
var chart = new google.visualization.ChartWrapper({
    'chartType': 'BarChart',
    'containerId': 'gct_combo_sample2_chart',
    'options': {hAxis:{format:'$#,###'}},
    'dataTable': data,
    // DataView の設定
    'view': {
        'columns': [0, 1]
    }
});
chart.draw();

連携

データを共有しただけでは、まだ連携とまでは言えません。 ここから表とグラフを連携させていきましょう。
連携できるのは次の 2 つです。
  1. 表のソート
  2. 選択
これらの連携には Google Chart Tools のイベント機能を利用します。
Google Chart Tools のグラフ(テーブル)では選択などの何らかのアクションを起こした時にイベントが発生します。 このイベントには addListener 関数を使ってコールバック関数の登録ができます。
登録されたコールバック関数はイベント発生時に呼び出されるので、 ここで連携用の処理を行います。

ソート

表をソートすると 'sort' イベントが発生します。
このイベントのコールバック関数内で表に合わせてデータをソートし、グラフを再描画します。
// データ定義
var data = new google.visualization.arrayToDataTable([
    ['名前', '給料', 'フルタイム', '入社年度'],
    ['Mike',  10000, true,         2000],
    ['Jim',   8000,  false,        2002],
    ['Alice', 12500, true,         1998],
    ['Bob',   7000,  true,         2001]
]);

// テーブルの作成
var formatter = new google.visualization.NumberFormat(
    {pattern: '$#,###'});
formatter.format(data, 1);
var formatter_year = new google.visualization.NumberFormat(
    {pattern: '#### 年'});
formatter_year.format(data, 3);

var table_option = {showRowNumber: true};
var table = new google.visualization.Table(
    document.getElementById('gct_combo_sample3_table'));
table.draw(data, table_option);


// DataView の作成
var vdata = new google.visualization.DataView(data);
vdata.setColumns([0, 1]);


// グラフの作成
var chart_option = {hAxis:{format:'$#,###'}};
var chart = new google.visualization.BarChart(
    document.getElementById('gct_combo_sample3_chart'));
chart.draw(vdata, chart_option);


// テーブルの sort イベントでグラフをソートする関数を呼び出す。
google.visualization.events.addListener(table, 'sort', function(event) {
    // イベントが発生した列でデータをソート(DataView ではない)
    data.sort([{column: event.column, desc: !event.ascending}]);
    // 再描画
    chart.draw(vdata, chart_option);
    
    // テーブルの選択状態をクリア
    table.setSelection(null);
});

なお、表の項目を選択したままソートするとデータだけ順番を変えるため、 選択対象がずれてしまいます。
これを保持するには対象の位置を調べて選択し直す必要があります。 ちょっと手間がかかるので、ソート後は選択状態を解除しています。

選択

選択の連携ではわかりやすいように、 まず組織図のサンプルで説明したいと思います。
Google Chart Tools で図を選択状態にするためには、setSelection() メソッドを実行します。
表を選択すると 'select' イベントが発生するので、 このとき、表の選択情報を getSelection() で取得し、グラフの setSelection() メソッドを呼び出します。
<script type="text/javascript" src="http://www.google.com/jsapi"></script>
<script type="text/javascript">
</script>

google.load('visualization', '1', {packages: ['orgchart', 'table']});
google.setOnLoadCallback(
    function () {
        var data = new google.visualization.DataTable();
        data.addColumn('string', '名前');
        data.addColumn('string', '管理者');
        data.addColumn('number', '給料');
        data.addColumn('boolean', 'フルタイム');
        data.addRows([
            ['Mike',  null,   {v: 20000, f: '$20,000'}, true ],
            ['Jim',   'Mike', {v: 8000,  f: '$8,000'},  true ],
            ['Alice', 'Mike', {v: 12500, f: '$12,500'}, false],
            ['Bob',   'Jim',  {v: 7000,  f: '$7,000'},  true ]
        ]);

        var org_view = new google.visualization.DataView(data);
        org_view.setColumns([0, 1]);
        
        var orgchart = new google.visualization.OrgChart(
            document.getElementById('gct_sample_orgchart_demo'));
        orgchart.draw(org_view, null);

        var table_view = new google.visualization.DataView(data);
        table_view.setColumns([0, 2, 3]);
        
        var table = new google.visualization.Table(
            document.getElementById('gct_sample_orgchart_demo_table'));
        table.draw(table_view, null);
        
        // テーブル選択時に組織図を選択
        google.visualization.events.addListener(table, 'select', function() {
            orgchart.setSelection(table.getSelection());
        });
        
        // 組織図選択時にテーブルを選択
        google.visualization.events.addListener(orgchart, 'select', function() {
            table.setSelection(orgchart.getSelection());
        });
    }
);

<div style="overflow-x: auto; padding:1px; margin-bottom: 1.2em;"><table>
  <tr>
    <td>
      <div id="gct_sample_orgchart_demo" style="width: 220px;"></div>
    </td>
    <td>
      <div id="gct_sample_orgchart_demo_table" style="width: 250px;"></div>
    </td>
  </tr>
</table></div>

最初のサンプルに戻りましょう。
先に別のサンプルを使ったのは、 棒(Bar)グラフと表の選択に対する連携では簡単にはいかない点があるためです。
組織図の場合と同じように書くと 表 → グラフ の連携はうまくいくのですが、 グラフ → 表 は連携しません

この原因は選択情報がグラフと表で少し違うためです。
棒(Bar)グラフのような多くのグラフでは、 getSelection() で取得される選択情報はデータテーブル上の行と列の番号を持ったオブジェクトの配列です。 これに対し、表は行のみの情報を持ったオブジェクトの配列です。

このため、表の選択時にはそのまま渡すのではなく、 一度列情報を消してからデータを渡すようにします。
 // テーブルで選択された時にグラフを選択する
 google.visualization.events.addListener(table, 'select', function() {
     chart.setSelection(table.getSelection());
 });
 
 // グラフで選択された時にテーブルを選択する
 google.visualization.events.addListener(chart, 'select', function() {
     var selection = chart.getSelection();
     for (var i = 0; i < selection.length; i++) {
        // 列情報を除去
        selection[i].column = null;
     }    
     table.setSelection(selection);
 });
ちなみに組織図は表と同じ行のみの情報なので、この場合はそのまま渡すことができます。
また、選択情報が配列になっているのは、 Google Chart Tools の図が Ctrl や Shift キーによって複数選択ができるようになっているためです。

ソートと選択を同時に連携

ソートと選択を同時に連携しようとした場合、少し問題が生じます。
ソート時にデータをソートしてグラフを再描画するため、 表とグラフで選択した項目が一致しないようになります。

これを解決するためには、 データのソート後にグラフだけでなく、表も再描画します。


しかし、表を再描画すると今度は別の問題が発生します。
再描画するため、ソートの矢印マークが消えてしまいます

これを回避するためには、再描画時に矢印を表示するようにオプションで指定します。
// データ定義
var data = new google.visualization.arrayToDataTable([
    ['名前', '給料', 'フルタイム', '入社年度'],
    ['Mike',  10000, true,         2000],
    ['Jim',   8000,  false,        2002],
    ['Alice', 12500, true,         1998],
    ['Bob',   7000,  true,         2001]
]);


// テーブルの作成
var formatter = new google.visualization.NumberFormat(
    {pattern: '$#,###'});
formatter.format(data, 1);
var formatter_year = new google.visualization.NumberFormat(
    {pattern: '#### 年'});
formatter_year.format(data, 3);

var table_option = {showRowNumber: true};
var table = new google.visualization.Table(
    document.getElementById('gct_combo_sample5_table'));
table.draw(data, table_option);


// DataView の作成
var vdata = new google.visualization.DataView(data);
vdata.setColumns([0, 1]);


// グラフの作成
var chart_option = {hAxis:{format:'$#,###'}};
var chart = new google.visualization.BarChart(
    document.getElementById('gct_combo_sample5_chart'));
chart.draw(vdata, chart_option);


// テーブルで選択された時にグラフを選択する
google.visualization.events.addListener(table, 'select', function() {
    chart.setSelection(table.getSelection());
});

// グラフで選択された時にテーブルを選択する
 google.visualization.events.addListener(chart, 'select', function() {
     var selection = chart.getSelection();
     for (var i = 0; i < selection.length; i++) {
        // 列情報を除去
        selection[i].column = null;
     }    
     table.setSelection(selection);
 });
 
 // テーブルの sort イベントでグラフをソートする関数を呼び出す。
 google.visualization.events.addListener( table, 'sort', function(event) {
     // イベントが発生した列でデータをソート(DataView ではない)
     data.sort([{column: event.column, desc: !event.ascending}]);
 
     // グラフの再描画
     chart.draw(vdata, chart_option);
 
     // テーブルの再描画
     table_option['sortAscending'] = event.ascending; // ソート昇降順
     table_option['sortColumn'] = event.column; // ソート列
     table.draw(data, table_option);
 
     // テーブルの選択状態をクリア
     table.setSelection(null);
 });
スポンサーサイト



 

Google Chart Tools - フィルタリング(Dashboard と Control)

今回は Google Chart Tools でフィルタリングの機能を提供する Dashboard と Control の説明です。

Control はフィルターの指定を受け取るための部品で、 Dashboards が Control とグラフを結びつける管理オブジェクトとなります。

使い方

Dashboards 、 Control を使ったフィルタリング機能の実現方法を説明します。

以下は数値範囲でフィルタリングするサンプルです。
スライダーで数値範囲を指定します。 この数値範囲に表示項目をフィルタリングしています。

<script type="text/javascript" src="https://www.google.com/jsapi"></script>
<script type="text/javascript">

  google.load('visualization', '1.0', {'packages':['controls']});
  google.setOnLoadCallback(drawFilteringChart);
  function drawFilteringChart() {
  
      var data = google.visualization.arrayToDataTable([
          ['名前', 'ドーナッツを食べた数'],
          ['Michael' , 5],
          ['Elisa', 7],
          ['Robert', 3],
          ['John', 2],
          ['Jessica', 6],
          ['Aaron', 1],
          ['Margareth', 8]
      ]);
  
      // グラフの作成
      var chart = new google.visualization.ChartWrapper({
          'chartType': 'PieChart',
          'containerId': 'filtering_chart_div',
          'options': {
              'pieSliceText': 'value'
          }
      });
  
  
      // Control の作成
      var control = new google.visualization.ControlWrapper({
        'controlType': 'NumberRangeFilter',
        'containerId': 'filtering_control_div',
        'options': {
            'filterColumnLabel': 'ドーナッツを食べた数'
        },
        'state' : {
            'lowValue' : 2
        }
      });
  
  
      // Dashboard の作成と関連付け
      var dashboard = new google.visualization.Dashboard(
        document.getElementById('filtering_dashboard_div'));
      dashboard.bind(control, chart);
  
      // Dashboard 描画(ここでグラフと Control も描画)
      dashboard.draw(data);
  
  }

</script>

<!-- Dashboard 用 div 要素 (Control 、 グラフの両方を中に含む) -->
<div id="filtering_dashboard_div">
  <!-- Control の div 要素 -->
  <div id="filtering_control_div"></div>
  <!-- グラフの div 要素 -->
  <div id="filtering_chart_div" style="width:60%;"></div>
</div>
全体的な記述の仕方は通常のグラフの書き方と同じです。 注意点としては次の 2 つでしょう。
  • ロードするパッケージが'controls'
  • 描画先の div 要素は 3 つ
    • グラフ用
    • Control 用
    • Dashboard 用 (グラフと Control の div 要素を中に持つ)
<script type="text/javascript" src="https://www.google.com/jsapi"></script>
<script type="text/javascript">
 </script>
   google.load('visualization', '1.0', {'packages':['controls']});
   google.setOnLoadCallback(drawFilteringChart);
   function drawFilteringChart() {
       // グラフとフィルターの作成
       //         :
   }
 <!-- Dashboard 用 div 要素 (Control 、 グラフの両方を中に含む) -->
 <div id="filtering_dashboard_div">
   <!-- Control の div 要素 -->
   <div id="filtering_control_div"></div>
   <!-- グラフの div 要素 -->
   <div id="filtering_chart_div" style="width:60%;"></div>
 </div>

グラフとフィルターの作成関数

グラフとフィルターの作成関数内の処理は次のような流れになります。
  1. データの作成
  2. グラフの作成
  3. Control の作成
  4. Dashboard で Control とグラフを結びつける
  5. Dashboard(グラフと Control) の描画
グラフに使用するデータの作成は他のグラフと同じです。

グラフの作成では、通常のグラフの作成と違い、 描画までは行いません。
グラフを Dashboard に関連付けた後、 Dashboard 内でグラフの描画を行います。

通常のグラフの描画時には draw 関数でデータとオプションを渡します。 データは Dashboard の draw 関数に渡すので問題ないのですが、 グラフの draw 関数を直接呼ばないとオプションを渡すことはできません。
このため、 グラフ描画をラップした ChartWrapper でグラフの作成を行います。
       // グラフの作成
       var chart = new google.visualization.ChartWrapper({
           'chartType': 'PieChart',
           'containerId': 'filtering_chart_div',
           'options': {
               'pieSliceText': 'value'
           }
       });
Control の作成でもグラフと同様に ControlWrapper を使用します。 使い方も ChartWrapper とほぼ同じです。

ここでのポイントはオプションの 'filterColumnLabel'フィルタリングの対象となる列を指定することです。
このサンプルではデータ作成時の 2 次元配列の 1 行目のラベル('ドーナッツを食べた数')を指定します。 これを指定していなかったり、ラベル名が違っていたりするとエラーとなります。

'filterColumnIndex' を使って列番号で対象を指定することもできます。

また、コントロールの場合、 オプションに似た 'state' を指定できます。 これでコントロールの初期状態を指定することができます。
      var control = new google.visualization.ControlWrapper({
        'controlType': 'NumberRangeFilter',
        'containerId': 'filtering_control_div',
        'options': {
            'filterColumnLabel': 'ドーナッツを食べた数'
        },
        'state' : {
            'lowValue' : 2
        }
      });
作成したグラフと Control のオブジェクトは bind メソッドで Dashboard に渡し、 Dashboard で管理するようにします。
Dashboard::bind(コントロール, グラフ)

最後にデータを渡して Dashboard の描画(draw)を実行します。
コントロール、 グラフの描画はこの関数内で実行されます。
Dashboard::draw(データ)
      // Dashboard の作成と関連付け
      var dashboard = new google.visualization.Dashboard(
        document.getElementById('filtering_dashboard_div'));
      dashboard.bind(control, chart);
  
      // Dashboard 描画(ここでグラフと Control も描画)
      dashboard.draw(data);
表との連携でおこなったように 1 つのデータに対して複数のグラフで表示したり、 列ごとに別のフィルターを使いたいといったこともあります。 こういった場合には bind() メッソドに渡す コントロール、 グラフはそれぞれ配列とすることもできます。

フィルタリング対象

フィルタリングではデータの列を指定し、 その列のデータがフィルター条件にマッチした行だけ表示します。
表示する列に対してフィルタリングはできません

例えば、次のような棒グラフでは表示する月はフィルタリングできますが、 表示する国のフィルタリングはできません。
['月',     'ボリビア', 'エクアドル', 'マダガスカル', 'パプアニューギニア', 'ルワンダ'],
['2004/05',       165,         938,             522,                 998,         450],
['2005/06',       135,         1120,            599,                 1268,        288],
['2006/07',       157,         1167,            587,                 807,         397],
['2007/08',       139,         1110,            615,                 968,         215],
['2008/09',       136,         691,             629,                 1026,        366]

Control の種類

利用可能な Control の 4 つです。
Control 名 フィルタリング対象
NumberRangeFilter 数値範囲
StringFilter 文字列
CategoryFilter カテゴリー(項目)
ChartRangeFilter グラフの表示範囲

数値範囲フィルター(NumberRangeFilter)

スライダーを使った数値範囲に対するフィルター。 前章のサンプルで使ったものです。

文字列フィルター(StringFilter)

文字列によるフィルターです。 指定した文字にマッチする項目のみ表示させます。
var data = google.visualization.arrayToDataTable([
    ['名前', '年齢'],
    ['Michael' , 12],
    ['Elisa', 20],
    ['Robert', 7],
    ['John', 54],
    ['Jessica', 22],
    ['Aaron', 3],
    ['Margareth', 42],
    ['Miranda', 33]
]);

// '名前' に対する文字列フィルター
var stringFilter = new google.visualization.ControlWrapper({
    'controlType': 'StringFilter',
    'containerId': 'string_filter_control_div',
    'options': {
        'filterColumnLabel': '名前'
    }
});

// var table = new google.visualization.ChartWrapper({
    'chartType': 'Table',
    'containerId': 'string_filter_chart_div'
});

var dashboard = new google.visualization.Dashboard(document.getElementById('string_filter_dashboard_div')).
    bind(stringFilter, table).
    draw(data);
よく使いそうなコントロールのオプションを挙げておきます。
名前 デフォルト値 説明
matchType string 'prefix' 文字列マッチのタイプ
'exact' : 完全一致
'prefix' : 前方一致
'any' : 文字列を含む
caseSensitive boolean false (区別しない) アルファベットの大文字、小文字を区別するかどうか
useFormattedValue boolean false (実際の値) format を使った場合に、フィルタリングの対象を表示上の値にするか、実際の値にするか

項目フィルター(CategoryFilter)

前の 2 つは指定した値にマッチした項目だけを表示しますが、 これは項目を直接選択するフィルターです。
var data = google.visualization.arrayToDataTable([
    ['名前', 'ドーナッツを食べた数'],
    ['Michael' , 5],
    ['Elisa', 7],
    ['Robert', 3],
    ['John', 2],
    ['Jessica', 6],
    ['Aaron', 1],
    ['Margareth', 8]
]);

var chart = new google.visualization.ChartWrapper({
    'chartType': 'PieChart',
    'containerId': 'category_filter_chart_div',
    'options': {
        'pieSliceText': 'value',
        'title': 'ドーナッツを食べた割合'
    }
});

// Control の作成
var control = new google.visualization.ControlWrapper({
    'controlType': 'CategoryFilter',
    'containerId': 'category_filter_control_div',
    'options': {
        'filterColumnLabel': '名前',
        'ui': {
            'allowMultiple': true,
            'caption': '値を選択...',
            'selectedValuesLayout': 'below'
        }
    },
    // 初期状態を指定
    'state': {'selectedValues': ['Michael', 'Aaron', 'John']}
});


var dashboard = new google.visualization.Dashboard(
    document.getElementById('category_filter_dashboard_div'));
dashboard.bind(control, chart);
dashboard.draw(data);
よく使いそうなオプションを次のようなものでしょう。
名前 デフォルト値 説明
useFormattedValue boolean false (実際の値) format を使った場合に、フィルタリングの対象を表示上の値にするか、実際の値にするか
ui.caption string 'Choose a value...' テキストボックス内に表示する文字列
ui.selectedValuesLayout string 'aside' 選択した値の表示形式(allowMultiple が true の場合)
  • 'aside': コントロールの横に配置
  • 'below': コントロールの下に配置
  • 'belowStacked': コントロールの下に配置し、下方向に増やす
  • 'belowWrapping': コントロールの下に配置し、 コントロール幅を超えたら折り返す
    js_gct_bellowWrapping.png
ui.allowMultiple boolean true 複数選択を許可するかどうか
ui.allowTyping boolean true 文字入力ができるかどうか。 false の場合は選択メニュー。
ui.label string auto コントロールにつけるラベル。 デフォルトでは列情報のラベル。

表示範囲フィルター(ChartRangeFilter)

グラフの表示範囲を制御します。
ChartRangeFilter ではコントロールもグラフです。
コントロール側のグラフの種類やオプションを指定するには ui.chartType, ui.chartOptions を使用します。 デフォルトは次の値です。
'ui': {
    'chartType' : 'ComboChart',
    'chartOptions': {
        'enableInteractivity': false,
        'chartArea': {'height': '100%'},
        'legend': {'position': 'none'},
        'hAxis': {'textPosition': 'in'},
        'vAxis': {
            'textPosition': 'none',
            'gridlines': {'color': 'none'}
        }
    }
}
グラフタイプのデフォルトである ComboChart に関しては以下をご覧下さい。 また、初期状態の表示範囲は 'state''range' オブジェクトで指定します。
// 値の作成
var data = new google.visualization.DataTable();
data.addColumn('date', '日付');
data.addColumn('number', '値');
var val = 0;
// 2012/1/1 から 4 ヶ月分のデータを追加
for (var day = 1; day < 121; ++day) {
    var change = (Math.sin(day / 2.5 + Math.PI) + Math.sin(day / 3) - Math.cos(day * 0.7)) * 150;
    val = val + change;
    val = Math.max(0, val);
    var date = new Date(2012, 0 ,day);
    data.addRow([date, Math.round(val)]);
}

var dashboard = new google.visualization.Dashboard(
    document.getElementById('chart_range_filter_dashboard_div'));

var control = new google.visualization.ControlWrapper({
    'controlType': 'ChartRangeFilter',
    'containerId': 'chart_range_filter_control_div',
    'options': {
        // 先頭列(データ項目)に対してフィルタリング
        'filterColumnIndex': 0,
        'ui': {
            'chartType' : 'LineChart',
            'chartOptions': {
                'hAxis': {'baselineColor': 'none'}
            },
            // 範囲の最小 : 2 日 = 2 * 24 * 60 * 60 * 1000 = 172,800,000 (msec.)
            'minRangeSize': 172800000
        }
    },
    // 初期範囲 2012/2/9 - 2012/3/20
    'state': {'range': {'start': new Date(2012, 1, 9), 'end': new Date(2012, 2, 20)}}
});

var chart = new google.visualization.ChartWrapper({
    'chartType': 'LineChart',
    'containerId': 'chart_range_filter_chart_div',
    'options': {
        'legend': {'position': 'none'}
    },
    // 1 列目を日付から文字列に変換
    'view': {
        'columns': [
            {
                'calc': function(dataTable, rowIndex) {
                    return dataTable.getFormattedValue(rowIndex, 0);
                },
                'type': 'string'
            }, 1]
    }
});     

dashboard.bind(control, chart);
dashboard.draw(data);
<div id="chart_range_filter_dashboard_div">
  <div id="chart_range_filter_chart_div" style='width:100%; height: 300px;'></div>
  <div id="chart_range_filter_control_div" style='width:100%; height: 50px;'></div>
</div>
サンプルではグラフでデータを使用するとき、 先頭列を日付オブジェクトから文字列に変換しています。
これは先頭列を X 軸の値ではなく、 データ項目(domain 名)として扱うためです。
    'view': {
        'columns': [
            {
                'calc': function(dataTable, rowIndex) {
                    return dataTable.getFormattedValue(rowIndex, 0);
                },
                'type': 'string'
            }, 1]
    }
 

Google Chart Tools - データロールによる特異点の表示と注釈付きタイムライン

Google Chart Tools のデータには役割(Role)があり、これを使ってグラフの特異点(注釈)などを表示することができます。 今回はこのデータロールについて説明したいと思います。
また、特異点の表示機能を強化した注釈付きタイムラインのグラフについても説明します。

データロール

DataTable に格納するデータは今まで通常のデータだけでした。
しかし、 DataTable に格納するデータにはロールを指定することができ、 これで注釈やツールチップなどを設定することができます。

特異点(注釈)の表示

最大値など特殊なデータの場合にグラフ上に印を付けたいことがあります。
'annotation' のデータロールを使うとこの印を表示することができます。
<script type="text/javascript" src="http://www.google.com/jsapi"></script>
<script type="text/javascript">

 google.load('visualization', '1', {packages: ['corechart']});
 google.setOnLoadCallback(
     function () {
        var data = new google.visualization.DataTable();
        data.addColumn('string', '年度');
        data.addColumn('number', '売上');
        data.addColumn({type:'string', role:'annotation'});
        data.addColumn({type:'string', role:'annotationText'});
        data.addRows([
             ['2006',  860, null, null],
             ['2007', 1030, null, null],
             ['2008',  350,  'A', 'リーマンショック'],
             ['2009',  805, null, null],
             ['2010',  880, null, null]
         ]);
        
         var options = {
             title: '会社業績'
         };
        
        var chart = new google.visualization.LineChart(document.getElementById('gct_data_role_annotate'));
         chart.draw(data, options);
     }
 );

</script>
 <div id="gct_data_role_annotate" style="width:60%; height:220px;"></div>
列を追加する際にロールとそのロールで使用する型を指定します。
'annotation' が印の文字で、'annotationText' が印のツールチップで表示されます。

annotation, annotationText は文字列(string)型ですが、 ロールによって使用する型は変わります。

ロールの種類

annotation, annotationText 以外にも様々なロールがあります。

確定(certainty)
確定 certainty はデフォルトでは true です。これを false にすると破線となります。
 data.addColumn('string', '年度');
 data.addColumn('number', '売上');
 data.addColumn({type:'boolean', role:'certainty'});
 data.addRows([
     ['2004', 1000, true ],
     ['2005', 1170, true ],
     ['2006',  660, false],      // false の前後が破線
     ['2007', 1030, true ]
 ]);
強調(emphasis)
データを強調表示します。
 data.addColumn('string', '年度');
 data.addColumn('number', '売上');
 data.addColumn({type:'boolean', role:'emphasis'});
 data.addRows([
     ['2004', 1000, false],
     ['2005', 1170, true ],      // true - true 間を強調
     ['2006',  660, true ],
     ['2007', 1030, false]
 ]);
間隔(interval)
interval のロールでは下限、上限の 2 つの値を指定して、間隔を表示します。
 data.addColumn('string', '日');
 data.addColumn('number', '在庫');
 data.addColumn({type:'number', role:'interval'}); // 下限
 data.addColumn({type:'number', role:'interval'}); // 上限
 data.addRows([
     ['月',  38,    20,   45],
     ['火',  55,    30,   66],
     ['水',  77,  null, null],
     ['木',  66,    50,   77]
 ]);
スコープ(scope)
スコープ外(false)が非強調されます。
 data.addColumn('string', '年度');
 data.addColumn('number', '売上');
 data.addColumn({type:'boolean', role:'scope'});
 data.addRows([
     ['2004', 1000, true ],
     ['2005', 1170, false],      // false - false 間がスコープ外
     ['2006',  660, false],
     ['2007', 1030, true ]
 ]);
ツールチップ(tooltip)
デフォルトでもデータポイントでツールチップが表示されますが、 tooltip ロールを使うと任意の文字列を指定出来ます。
 data.addColumn('string', '年度');
 data.addColumn('number', '売上');
 data.addColumn({type:'string', role:'tooltip'});
 data.addRows([
     ['2004', 1000, null],
     ['2005', 1170, null],
     ['2006',  660, null],
     ['2007', 1030, null]
 ]);
 // フォーマッターで、 0, 1 の列のデータから作ったデータを 2 列に格納
 var formatter = new google.visualization.PatternFormat('{0}年は ${1} の売上');
 formatter.format(data, [0, 1], 2);
一旦 null (デフォルトのまま) を指定し、PatternFormatter を使って指定しています。

項目(domain)
通常、データ項目(ドメイン)は先頭列のみですが、 domain ロールを使うと複数指定することができます。複数指定した場合にはグラフ上で併記されます。
 data.addColumn({type: 'string', role: 'domain'}, '2009 Quarter');
 data.addColumn('number', '2009 売上');
 data.addColumn({type: 'string', role: 'domain'}, '2008 Quarter');
 data.addColumn('number', '2008 売上');
 data.addColumn({type:'boolean', role:'certainty'});
 data.addRows([
     ['Q1 2009', 1000, 'Q1 2008', 800, false],
     ['Q2 2009', 1170, 'Q2 2008', 750, false],
     ['Q3 2009', 660,  'Q3 2008', 700, false],
     ['Q4 2009', 1030, 'Q4 2008', 820, false]
 ]);
 var chart = new google.visualization.LineChart(document.getElementById('gct_data_role_domain'));
 chart.draw(data, {focusTarget: 'category', title: '四半期別2009年度売上'});
2009 年の売上に 2008 年を比較として載せています。

注釈付きタイムライン

Google Chart Tools では注釈付きタイムライン (Annotated Time Line) というグラフがあります。
これはベースは折れ線(面積)グラフですが次の特徴があります。
  • X 軸が時間
    • 先頭列は Data か DataTime オブジェクト
  • 注釈を表示
    • 通常のグラフと違い、選択可能
  • 標準で表示領域のフィルター付き
  • fill オプションで面積グラフに
    • 0 - 100 の値で透過率を指定 ( 0 が非表示 )
  • ローカルファイル(file:///) では使用できない
<script type="text/javascript" src="http://www.google.com/jsapi"></script>
<script type='text/javascript'>

google.load('visualization', '1', {'packages':['annotatedtimeline']});
google.setOnLoadCallback(
    function () {
        var data = new google.visualization.DataTable();
        data.addColumn('date', 'Date');
        data.addColumn('number', '鉛筆の売上');
        data.addColumn('string', '注釈タイトル 1');
        data.addColumn('string', '注釈説明 1');
        data.addColumn('number', 'ペンの売上');
        data.addColumn('string', '注釈タイトル 2');
        data.addColumn('string', '注釈説明 2');
        data.addRows([
            [new Date(2008, 1 ,1), 30000, undefined, undefined, 40645, undefined, undefined],
            [new Date(2008, 1 ,2), 14045, undefined, undefined, 20374, undefined, undefined],
            [new Date(2008, 1 ,3), 55022, undefined, undefined, 50766, undefined, undefined],
            [new Date(2008, 1 ,4), 75284, undefined, undefined, 14334,
             '在庫切れ','午後 4 時に在庫がなくなった'],
            [new Date(2008, 1 ,5), 41476, 'ペン販売を再開','200k 本のペンを売り上げた',
             66467, undefined, undefined],
            [new Date(2008, 1 ,6), 33322, undefined, undefined, 39463, undefined, undefined]
        ]);

        var chart = new google.visualization.AnnotatedTimeLine(
            document.getElementById('gct_annotatedtimeline_div'));
        chart.draw(data, {displayAnnotations: true, fill: 25});
    }
);

</script>
<div id='gct_annotatedtimeline_div' style='width: 100%; height: 240px;'></div>
 
このページをシェア
アクセスカウンター
アクセスランキング
[ジャンルランキング]
コンピュータ
26位
アクセスランキングを見る>>

[サブジャンルランキング]
プログラミング
8位
アクセスランキングを見る>>
カレンダー(アーカイブ)
プルダウン 降順 昇順 年別

12月 | 2013年01月 | 02月
- - 1 2 3 4 5
6 7 8 9 10 11 12
13 14 15 16 17 18 19
20 21 22 23 24 25 26
27 28 29 30 31 - -


はてな新着記事
はてな人気記事
ブロとも申請フォーム
プロフィール

yohshiy

Author:yohshiy
職業プログラマー。
仕事は主に C++ ですが、軽い言語マニアなので、色々使っています。

はてブ:yohshiy のブックマーク
Twitter:@yohshiy

サイト紹介
プログラミング好きのブログです。プログラミング関連の話題や公開ソフトの開発記などを雑多に書いてます。ただ、たまに英語やネット系の話になることも。