iT邦幫忙

2017 iT 邦幫忙鐵人賽
DAY 16
2
Modern Web

Webduino 不只是物聯網,智慧插座也可以很 Modern~系列 第 16

實戰智慧插座 16 - 搖搖手機就開燈 ( 行動裝置陀螺儀、加速度計 )

玩過人臉追蹤與顏色追蹤之後,接著把焦點拉回手機上,既然我們可以透過網頁做這麼多事情,如果用手機或平板打開網頁,能否發揮行動裝置的優勢呢?這篇文章將會介紹如何透過網頁獲取行動裝置陀螺儀的數值 ( 前後左右翻轉 ),然後把這些數值拿來控制智慧插座的電燈泡。



獲取陀螺儀數值

講到行動裝置陀螺儀就要參考我之前寫的文章:OXXO.STUDIO ~ HTML5 控制裝置陀螺儀 ( 三軸 ),要使用行動裝置的陀螺儀,我們只要監聽 deviceorientation 的事件就可以,它的用法和 click 是一模一樣。

window.addEventListener('deviceorientation', function(event) {
  var alpha = event.alpha;
  var beta = event.beta;
  var gamma = event.gamma;
}, false);

從上述最基本的程式碼中可以看到,這個事件有三個 API,分別是:alpha、beta 以及 gamma,這三個 API 代表甚麼意思呢?下面三張圖分別表現三個軸轉動的角度和方向。

  • aplha
    行動裝置水平放置時,繞 Z 軸旋轉的角度,數值為 0 度到 360 度。
    Webduino 手機陀螺儀

  • beta
    行動裝置水平放置時,繞 X 軸旋轉的角度,數值為 -180 度到 180 度。
    Webduino 手機陀螺儀

  • gamma
    行動裝置水平放置時,繞 Z 軸旋轉的角度,數值為 -90 度到 90 度。
    Webduino 手機陀螺儀

接著就用簡單的範例來測試看看,下面的範例我在畫面中放入三個區塊,分別代表 alpha、beta 與 gamma,當用手機打開這個網頁,轉動手機就會看到數值的變化,此外在一開始也加入一個判斷式,如果手機不支援,則會顯示不支援的文字訊息,判斷的方式為讀取 window 是否有 DeviceOrientationEvent 這個屬性,其實我們也可以從瀏覽器的 console 裏頭看到 window 是否有包含這個屬性。

理解之後就看一下程式碼,HTML 就擺上三個區塊。

alpha:<span id="alpha"></span><br/>
beta:<span id="beta"></span><br/>
gamma:<span id="gamma"></span><br/>

Javascript 的部分利用 window.addEventListener 監聽 deviceorientation 事件,接著就可以獲取 alpha、beta 和 gamma,不過獲取到的數值其實是個有非常多個小數點位數的數值,再利用 Math.round 來四捨五入。

if(window.DeviceOrientationEvent) {
  window.addEventListener('deviceorientation', function(event) {
  var a = document.getElementById('alpha'),
        b = document.getElementById('beta'),
        g = document.getElementById('gamma'),
        alpha = event.alpha,
        beta = event.beta,
        gamma = event.gamma;

  a.innerHTML = Math.round(alpha);
  b.innerHTML = Math.round(beta);
  g.innerHTML = Math.round(gamma);

    }, false);
}else{
    document.querySelector('body').innerHTML = '你的瀏覽器不支援喔';
}

完成後,用手機打開旋轉一下,應該就可以看到數值的變化了。
Webduino 手機陀螺儀
( 程式:http://bin.webduino.io/ribuq/4/edit?html,css,js,output )



獲取加速度計數值

除了可以偵測旋轉與翻轉之外,現在也可以透過 devicemotion,從行動裝置的加速度計獲得三個維度的加速度。

window.addEventListener('devicemotion', function(evnet) {
  var x = event.acceleration.x;
  var y = event.acceleration.y;
  var z = event.acceleration.z;
}, false);

實際上 devicemotion 還可以做得更多

// 加速感測包括重力參數
event.accelerationIncludingGravity.x
event.accelerationIncludingGravity.y
event.accelerationIncludingGravity.z

// 旋轉率
event.rotationRate.alpha
event.rotationRate.beta
event.rotationRate.gamma

實際做個網頁測試一下,這邊有利用 Math.round 來四捨五入。

if(window.DeviceOrientationEvent) {
  window.addEventListener('devicemotion', function(event) {
  var tx = document.getElementById('tx’)',
        ty = document.getElementById('ty'),
          tz = document.getElementById('tz'),
          x = event.acceleration.x,
          y = event.acceleration.y
          z = event.acceleration.z;

    tx.innerHTML = Math.round(x);
    ty.innerHTML = Math.round(y);
    tz.innerHTML = Math.round(z);

    }, false);
}else{
    document.querySelector('body').innerHTML = '你的瀏覽器不支援喔';
}

完成後,把手機上下左右移動,就可以看到加速度變化。
Webduino 手機陀螺儀
( 程式:http://bin.webduino.io/xiqiy/1/edit?html,css,js,output )



左右翻轉點亮燈泡

知道原理之後我們就來控制實際的插座,首先我們先來測試「左右翻轉」,往左翻就開燈,往右翻就關燈,網頁上就只顯示數值就可以,HTML 先引入對應的 JavaScript,放入一個 h2 顯示文字。

<html>
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no">
  <title>Webduino</title>
  <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
  <script src="https://webduino.io/components/webduino-js/dist/webduino-all.min.js"></script>
  <script src="https://blockly.webduino.io/webduino-blockly.js"></script>
</head>

<body>
  <h2 id="show"></h2>
</body>
</html>

再來看到 JavaScript,把剛剛上面介紹過的程式碼複製下來用,記得要寫入裝置的程式碼,然後讓我這邊是讓 gamma 數值大於零 ( 也就是往右翻 ) 的時候會開燈。( 其實你也可以放 12 個燈泡圍成一個圈,透過 aplha 的數值,就可以轉到哪個燈泡,哪個燈泡就亮起來 )

$(function(){

  var led, aplha, beta, gamma;
      $show=$('#show');

  //裝置連線
  boardReady('你的裝置 ID', function (board) {
    $show.html('準備中...');
    board.systemReset();
    board.samplingInterval = 250;
    board.autoReconnect = true;
    led = getLed(board, 10); //設定 LED 為 10 號腳

    if(window.DeviceOrientationEvent) {
      window.addEventListener('deviceorientation', function(event) {
        var alpha = Math.round(event.alpha),
            beta = Math.round(event.beta),
            gamma = Math.round(event.gamma);

        $show.html(gamma); //左右翻轉使用 gamma
        if(gamma>0){
          led.on();
        }else{
          led.off();
        }

      }, false);
    }else{
        $show.html('瀏覽器不支援');
    }
  });

});

最後的結果如下,當我們翻轉手機,燈泡就會亮起。
Webduino 手機陀螺儀
( 程式:http://bin.webduino.io/coqez/1/edit?html,js,output )



搖動手機點亮燈泡

除了翻轉手機,也可以透過加速度來開燈,這邊我實作一個搖一搖手機就開燈的效果,因為手機可能隨時都在動,就算我們認為是上下晃,左右晃的程度也要考慮進去,所以這裡最主要這邊有設定一個搖動的臨界值 shak_threshold,然後透過時間差的換算,就可以在我們想要的晃動幅度,進行我們指定的流程。

$(function(){

  var $show=$('#show'),
      led,x,y,z, 
      a = 0,
      shak_threshold = 2000,
      last_update = 0,
      last_x = 0,
      last_y = 0,
      last_z = 0;

  //裝置連線
  boardReady('你的裝置 ID', function (board) {
    $show.html('準備中...');
    board.systemReset();
    board.samplingInterval = 250;
    board.autoReconnect = true;
    led = getLed(board, 10); //設定 LED 為 10 號腳

    if(window.DeviceMotionEvent) {
      window.addEventListener('devicemotion', function(event) {

        var acceleration = event.accelerationIncludingGravity;
        var curTime = new Date().getTime(); //獲取當前時間
        if((curTime - last_update) > 100){
    //設定間隔時間,避免短時間的內的晃動干擾
            var diffTime = curTime - last_update;
            last_update = curTime;
            x = Math.round(acceleration.x);
            y = Math.round(acceleration.y);
            z = Math.round(acceleration.z);
    //計算晃動速度
            var speed = Math.abs((x + y + z - last_x - last_y - last_z)) / diffTime * 10000;
            $show.html(speed);
            if(speed > shak_threshold && a<1){
              a = 1;
              led.on();
              setTimeout(function(){
                led.off();
                a = 0;
              },1000);
            }
        }

      }, false);
    }else{
        $show.html('瀏覽器不支援');
    }
  });

});

最後的結果如下,當我們搖動手機到一定程度,燈泡就會亮起。
Webduino 手機陀螺儀
( 程式:http://bin.webduino.io/rahiq/1/edit?html,js,output )



小結

如果不太會寫程式,其實 Webduino Blockly 編輯工具 ( https://blockly.webduino.io ) 也提供了手機陀螺儀與加速度計的功能,有興趣也可以使用看看,打開下面的範例網頁,點選右上角的 QRCode 用手機掃描就可以囉!

手機陀螺儀 ( http://blockly.webduino.io/#-K_Dv_47bY4xaMvf65pk )
Webduino 手機陀螺儀

手機加速度計 ( http://blockly.webduino.io/#-K_DvO27DPYUwAt6rUi8 )
Webduino 手機陀螺儀

參考資訊:


上一篇
實戰智慧插座 15 - 臉色發青就開燈 ( 人臉追蹤、顏色追蹤 )
下一篇
實戰智慧插座 17 - 用網頁聊天室開關燈 ( 聊天室原理篇 )
系列文
Webduino 不只是物聯網,智慧插座也可以很 Modern~30

尚未有邦友留言

立即登入留言