Google公式User Guide勝手翻訳


共通プログラミングタスク



カスタムメニューとポップアップメッセージの制作

スプレッドシートにカスタムメニューを追加して、スクリプトの特定の関数へリンクするように、メニューアイテムを加えるのは難しいことではない。
簡単な例を示そう。メニューバーSurpreisesというメニューを追加する。そこにはメニューアイテムは二つ、Surprise 1Surprise 2だ。その内のどちらか一つを選ぶと、それによって関数はメッセージボックスを表示する。


function onOpen() {
 
var ss = SpreadsheetApp.getActiveSpreadsheet();
 
var menuEntries = [ {name: "Surprise 1", functionName: "menuItem1"},
                     
{name: "Surprise 2", functionName: "menuItem2"} ];
  ss
.addMenu("Surprises", menuEntries);
}

function menuItem1() {
 
Browser.msgBox("You clicked Surprise 1 on the menu!");
}

function menuItem2() {
 
Browser.msgBox("Surprise! Surprise!")
}

普通は、スプレッドシートが開かれると同時に、カスタムメニューが表示されるようにしたいと思うだろう。それをするには、onOpen関数をスクリプトに含めればいい。これらの関数はスプレッドシートが開かれると同時に実行される。ユーザーがすぐ見られるようにメニューとデーターでスプレッドシートを最初から埋めるのに便利だ。

スクリプト例では、メニューエントリは次のコードのように定義されている。

  var menuEntries = [ {name: "Surprise 1", functionName: "menuItem1"},
                     
{name: "Surprise 2", functionName: "menuItem2"} ];

変数menuEntriesはオブジェクトの配列をとる。それぞれのオブジェクトは、名前と関数名キーを一セットで持っている。配列は要素の集合でスプレッドシートのような感じで働くものである。それぞれの配列要素は配列の位置、インデックスポイントと呼ばれる、で識別される。JavaScriptの配列とGoogle Appsスクリプトはゼロが起点となる。最初の要素は1じゃなくて0ということである。例えばもし3x2の配列なら、最初の場所は0,0となる。配列は、プログラムやスクリプト内でデータを操作するのに便利な方法である。メニューアイテムは配列内にあるといえる。なぜなら、メニュー名と関数が角括弧っでかこまれてるから。それぞれのメニューアイテムは中括弧に置かれ、この構文はそれぞれの名前-関数ペアをオブジェクトとして定義している。

メニューエントリの定義のあとはメニューそのものの定義が来る

ss.addMenu("Surprises", menuEntries);

メニューラベルはSurprisesで、menuEntriesaddMenuメソッドの引数となり、メニューアイテム名とリンクする関数名を定義する配列による値をパスする。

ここに一般的なメニューを作成するコードを示す

function onOpen() {
 
var ss = SpreadsheetApp.getActiveSpreadsheet();
 
var menuEntries = [ {name: "item_name_1", functionName: "function_1"},
                     
{name: "item_name_2", functionName: "function_2"},
           
{name: "item_name_n", functionName: "function_n"];
  ss
.addMenu("menu_name", menuEntries);
}

次のコードは新たなメニューのメニューアイテムを選択した時にメッセージボックスを表示させる。

function menuItem1() {
 
Browser.msgBox("You clicked Surprise 1 on the menu!");

次は普遍化されたコード

function yourFunctionName() {
 
Browser.msgBox("message_to_display");

menuEntries配列で使う名前を関数に与える。そしてBrowserクラスのmsgBoxメソッドを呼び出し、表示させたいメッセージを引数としてとる。


より良いパフォーマンスのためのスクリプトの最適化

ただ二つの基本原則を理解するだけで、スクリプトから最大限のパフォーマンスを引き出すことができる

  • 他のサービスの呼び出しを最小化する
  • パッチ処理をできるだけ使う
次の二つの章でこの原則の詳細を見てみよう。

他サービス呼び出しの最小化

JavaScriptの処理は他のサービスと通信するよりかなり早い。Appsスクリプト内での処理はスプレッドシートやドキュメントやサイトや翻訳などなどを呼び出すよりずっと速い。なので、これらの他サービス呼び出しの最小化の方法を見つけられれば、スクリプトはずっと速く動く。


バッチ処理の使用

スクリプトはスプレッドシートからデータを読み、計算をし、結果を書き込む必要がある。Appsスクリプトは先読みを使って最適化する機能をすでに持っている。


キャッシュを使って、読み込み書き込みを最小化する最適化機能を最大限に生かしてスクリプトを書く事ができる。読み書きコマンドは遅い。スクリプトをスピードアップするために、配列に一回の命令で全てのデータを読み込み、配列のデータを使って様々な処理を行い、再び一回の命令でデータを書き込む。

例は次に示す。これは使うべきでない悪い例。スクリプトギャラリーにあるSpreadsheet Fractal Artは100 x 100 マスすべてに背景色をセットするために次のゴードを使ってる。

// このコードは使用してはならない。 遅くて、非効率なコードの例である。
//デモ使用のみ。

var cell = sheet.getRange('a1');
for (var y = 0; y < 100; y++) {
  xcoord
= xmin;
 
for (var x = 0; x < 100; x++) {
   
var c = getColor_(xcoord, ycoord);
    cell
.offset(y, x).setBackgroundColor(c);
    xcoord
+= xincrement;
 
}
  ycoord
-= yincrement;
 
SpreadsheetApp.flush();
}

このスクリプトは非効率的である。100行、100列のループを繰り返し、10000セルに絶え間なく書き込む。このときAppsスクリプトのライトバックキャッシュが働き,全てのラインの最後でデータをフラッシュする。キャッシュのお陰で、100回だけスプレッドシートを呼び出すだけですんでいる。

しかしコードは呼び出しをまとめることでもっと効率的になる。上を書きなおして、colorsという配列にセル範囲を読み込み、背景色処理は配列内のデータで行い、配列の値はスプレッドシートに書き込まれる。

// この例は使用してもOK
var cell = sheet.getRange('a1');
var colors = new Array(100);
for (var y = 0; y < 100; y++) {
  xcoord
= xmin;
  colors
[y] = new Array(100);
 
for (var x = 0; x < 100; x++) {
    colors
[y][x] = getColor_(xcoord, ycoord);
    xcoord
+= xincrement;
 
}
  ycoord
-= yincrement;
}
sheet
.getRange(1, 1, 100, 100).setBackgroundColors(colors);

非効率的なコードは70秒ほどかかるのに対して、効率的なコードは一秒しかかからない。

フラクタルアートスクリプトをもし見てるなら、我々がちょっとばかりの変更を、例をわかりやすくするためにくわえてることに注意していただきたい。実際に公開されてるスクリプトは、setBackgroundRGBコールを使っていて、上記のようにsetBackgroundColorは使っていない。getColor_関数は次のように変更されている。

if (iteration == max_iteration) {
   
return "#000000";
} else {
   
var c = 255 - (iteration * 5);
   c
= Math.min(255, Math.max(0, c));
   
var hex = Number(c).toString(16);
   
while (hex.length < 2)
     hex
= "0" + hex;
   
   
return ("#"+hex+"3280");
}


スクリプトからEmailを送る

二つのGoogle Apps Script チュートリアル

スクリプトからメールの送り方