4
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

GASでアプリを作ったら驚くほど英単語が覚えられるようになった話②

Last updated at Posted at 2020-09-22

前回(https://qiita.com/HIROKOBA/items/11fecc2e1afa4ac29f32) からの続きになります。

①自分用にカスタマイズした単語だけが
②ランダムに
③決まった時間に
④自動的に出題されてくる
。。。という機能の単語帳をGASとLINEを使って作ったよという話です。

ほぼ素人の状態で書いたコードなのですが、一応ちゃんと動いています。

//8つのトリガーを実施する関数
function setTrigger() {
  setTrigger1();
  setTrigger2();
  setTrigger3();
  setTrigger4();
  setTrigger5();
  setTrigger6();
  setTrigger7();
  setTrigger8();
}

//7時に時間を指定
function setTrigger1() {
  var triggerDay = new Date();
  triggerDay.setHours(07);
  triggerDay.setMinutes(00);
  ScriptApp.newTrigger("getPhrase").timeBased().at(triggerDay).create();
}

//9時に時間を指定
function setTrigger2() {
  var triggerDay = new Date();
  triggerDay.setHours(09);
  triggerDay.setMinutes(00);
  ScriptApp.newTrigger("getPhrase").timeBased().at(triggerDay).create();
}

//11時に時間を指定
function setTrigger3() {
  var triggerDay = new Date();
  triggerDay.setHours(11);
  triggerDay.setMinutes(00);
  ScriptApp.newTrigger("getPhrase").timeBased().at(triggerDay).create();
}

//13時に時間を指定
function setTrigger4() {
  var triggerDay = new Date();
  triggerDay.setHours(13);
  triggerDay.setMinutes(00);
  ScriptApp.newTrigger("getPhrase").timeBased().at(triggerDay).create();
}

//15時に時間を指定
function setTrigger5() {
  var triggerDay = new Date();
  triggerDay.setHours(15);
  triggerDay.setMinutes(00);
  ScriptApp.newTrigger("getPhrase").timeBased().at(triggerDay).create();
}

//17時に時間を指定
function setTrigger6() {
  var triggerDay = new Date();
  triggerDay.setHours(17);
  triggerDay.setMinutes(00);
  ScriptApp.newTrigger("getPhrase").timeBased().at(triggerDay).create();
}

//19時に時間を指定
function setTrigger7() {
  var triggerDay = new Date();
  triggerDay.setHours(19);
  triggerDay.setMinutes(00);
  ScriptApp.newTrigger("getPhrase").timeBased().at(triggerDay).create();
}

//21時に時間を指定
function setTrigger8() {
  var triggerDay = new Date();
  triggerDay.setHours(21);
  triggerDay.setMinutes(00);
  ScriptApp.newTrigger("getPhrase").timeBased().at(triggerDay).create();
}

//lineトークンなどを入力(XXX...はLine Developersで取得したアクセストークンやユーザーID)
const lineToken = 'XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX';
const userID = 'XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX';
const endPoint = 'https://api.line.me/v2/bot/message/push';
const spreadSheet = SpreadsheetApp.getActiveSpreadsheet().getActiveSheet();
const lastRow = spreadSheet.getLastRow();
const range = spreadSheet.getRange(1,1,lastRow-1,2);//シートのA1:B最終行の範囲を取得
const values = range.getValues();//取得した範囲の値を取得

/**  
SpreadSheetから英語フレーズを取得
**/
function getPhrase(){

//ボタンを押して表示させた単語がリストに登録されてしまうので毎回コード起動時に余計な解答を削除
  deleteRows();

  //単語1用の乱数を作成
  const randomValues = Math.floor(Math.random() * values.length);//valuesの数で乱数を作成
  const randomValues2 = Math.floor(Math.random() * 2);
  const resultValues = values[randomValues][randomValues2];//問題として出題される要素
  var otherValues1 = 0;
  if(randomValues2 == 0){
    otherValues1 = 1;
  }
  const Answer = values[randomValues][otherValues1];

  //単語2用の乱数を作成
  const randomValues3 = Math.floor(Math.random() * values.length);//valuesの数で乱数を作成
  const randomValues4 = Math.floor(Math.random() * 2);
  const resultValues2 = values[randomValues3][randomValues4];//問題として出題される要素
  var otherValues2 = 0;
  if(randomValues4 == 0){
    otherValues2 = 1;
  }
  const Answer2 = values[randomValues3][otherValues2];
  
  //単語3用の乱数を作成
  const randomValues5 = Math.floor(Math.random() * values.length);//valuesの数で乱数を作成
  const randomValues6 = Math.floor(Math.random() * 2);
  const resultValues3 = values[randomValues5][randomValues6];//問題として出題される要素
  var otherValues3 = 0;
  if(randomValues6 == 0){
    otherValues3 = 1;
  }
  const Answer3 = values[randomValues5][otherValues3];
  
  //単語4用の乱数を作成
  const randomValues7 = Math.floor(Math.random() * values.length);//valuesの数で乱数を作成
  const randomValues8 = Math.floor(Math.random() * 2);
  const resultValues4 = values[randomValues7][randomValues8];//問題として出題される要素
  var otherValues4 = 0;
  if(randomValues8 == 0){
    otherValues4 = 1;
  }
  const Answer4 = values[randomValues7][otherValues4];
  
  //単語5用の乱数を作成
  const randomValues9 = Math.floor(Math.random() * values.length);//valuesの数で乱数を作成
  const randomValues10 = Math.floor(Math.random() * 2);
  const resultValues5 = values[randomValues9][randomValues10];//問題として出題される要素
  var otherValues5 = 0;
  if(randomValues10 == 0){
    otherValues5 = 1;
  }
  const Answer5 = values[randomValues9][otherValues5];   

//問題がボタン形式で送信されてくる設定
  const headers = {
    'Content-Type':'application/json; charset=UTF-8',
    'Authorization': 'Bearer ' + lineToken
  };

  const data = {
    'to': userID,
    'messages':[
      {
      "type": "template",
      "altText": "It's English time!",
      "template": {
        "type":"buttons",
        "text":resultValues,
        "actions": [
          {
          "type": "message",
          "label": "Check answer!",
          "text": Answer,
          }
        ]
      }
      },
      {
      "type": "template",
      "altText": "It's English time!",
      "template": {
        "type":"buttons",
        "text":resultValues2,
        "actions": [
          {
          "type": "message",
          "label": "Check answer!",
          "text": Answer2,
          }
        ]
      }
      },
      {
      "type": "template",
      "altText": "It's English time!",
      "template": {
        "type":"buttons",
        "text":resultValues3,
        "actions": [
          {
          "type": "message",
          "label": "Check answer!",
          "text": Answer3,
          }
        ]
      }
      },
      {
      "type": "template",
      "altText": "It's English time!",
      "template": {
        "type":"buttons",
        "text":resultValues4,
        "actions": [
          {
          "type": "message",
          "label": "Check answer!",
          "text": Answer4,
          }
        ]
      }
      },
      {
      "type": "template",
      "altText": "It's English time!",
      "template": {
        "type":"buttons",
        "text":resultValues5,
        "actions": [
          {
          "type": "message",
          "label": "Check answer!",
          "text": Answer5,
          }
        ]
      }
      }
    ]
  };

  const options = {
    'method': 'post',
    'headers': headers,
    'payload' : JSON.stringify(data)
  };
  return UrlFetchApp.fetch(endPoint, options);
}

//解答を表示するとスプレッドシートに登録されてしまうのでその分を毎回削除
function deleteRows(){
  for(i = lastRow; i >=1; i--){
    var cell = spreadSheet.getRange(i,2)
    if(cell.isBlank()){
      spreadSheet.deleteRow(i);
    }
  }
};


/***
ユーザーからメッセージ投稿でスプレットシートに書き込み
***/
function doPost(e) {
   // 送信されてきたメッセージを取得
  const message_text = JSON.parse(e.postData.contents).events[0].message.text;
   // messageTextに\nが含まれているかの判定
  const split_flg = message_text.match('\n');
   // True = 区切り位置を改行にしリスト化
    if(split_flg != null){
      const message_list = message_text.split('\n');
      spreadSheet.appendRow([message_list[0],message_list[1]]);
    }else{
      spreadSheet.appendRow([message_text]);
    }
};

毎日決まった時間にスプレッドシートからLINEに日本語or英語の単語が出題されてきて、ボタンを押すと解答(問題が日本語なら英語、英語なら日本語)が出てくるという簡単な単語帳です。あとLINEの画面から単語登録できるようにしたのがとても便利で、知らない単語が出てきたらほとんど無意識に登録するようになっていました。

1年くらい前に初めて自分でコード書いて、LINEやGASのリファレンスと格闘しながら作りました。。でも完成してみると決まった時間に有無を言わさず問題が送られてきて、空き時間に勉強できるので(タイトルに書いた通り)驚くくらい英単語が頭に入ってくるようになりました。アメリカのYahooニュースの記事に登場する単語は、ほぼ全て分かるというくらいのレベルです。

今はRubyを勉強していますが、GASとLINEはものすごく相性がいいなと感じたのでまたアイデアを思いついたらいろいろ作ってみたいです。

4
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
4
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?