この記事は

です。

人に会う仕事、接客する仕事に携わる人たちは、表情にとても気を使っています。
毎日鏡に向かって笑顔を作り、良い笑顔ができているかどうか、チェックする人も多いと聞きます。

しかし、自分が作った笑顔が魅力的かどうか、自分自身ではなかなか判断がつかないもの。

そこで、MS AzureCognitive Services の一つ、Emotion API を利用して

「あなたの笑顔が魅力的かどうか、AIに判断してもらおう!」

という (お遊び) アプリを作ってみました。

実際の挙動

フォームから、自分の表情を写真で撮影し、アプリにアップロードします。
(ここではサンプルの写真を利用。「ぱくたそ」「フォト蔵」さんからお借りしました。)

サンプル1

sc_1.jpg

最初の写真。とても素敵な笑顔です。

sc_2.jpg

AIも、「最高の笑顔です」と認識してくれました。

サンプル2

sc_3.jpg

ややアルカイックスマイル気味ですが、素敵な笑顔です。

sc_4.jpg

やはり良い笑顔と判定してくれたようです。

サンプル3

sc_5.jpg

どうすれば人々は苦しみから開放されるのか、悩んでいるのでしょうか。
憂いを秘めた表情です。

sc_6.jpg

AIは「お疲れのご様子ですね」と判断したようです。

このように、素敵な笑顔を作れているかどうか、アプリ が診断してくれます。

仕様

Emotion API に対して、人間の表情が写っている写真を投げると、JSONのレスポンスデータが返って来ます。

emotion_top.png

画像は、Emotion API のページからキャプチャしたものです。サンプルの写真と、写真に対する返り値のJSONが表示されています。このJSONデータには、表情から感情を読み取り、各種の感情をパラメーター化した結果が含まれています。

 JSON:
 [
  {
    "faceRectangle": {
      "top": 114,
      "left": 212,
      "width": 65,
      "height": 65
    },
    "scores": {
      "anger": 1.0570484E-08,
      "contempt": 1.52679547E-09,
      "disgust": 1.60232943E-07,
      "fear": 6.00660363E-12,
      "happiness": 0.9999998,
      "neutral": 9.449728E-09,
      "sadness": 1.23025981E-08,
      "surprise": 9.91396E-10
    }
  },

レスポンスデータの「scores」には、怒り(anger)、恐れ(fear)、幸せ(hapiness)などの各種パラメーターが、最低値0-最高値1の間の値で付与されています。

今回のスマイルチェッカーでは

  • 良い笑顔 = 幸せ度数が高い笑顔

と定義して、返り値のJSONから「hapiness」の値を抽出。hapiness値が高い= 素敵な笑顔、として判断するようにしました。

Emotion API の準備

まず最初に、Emotion API を利用できるよう、Azure からAPIキーを発行します。Azure のダッシュボードから
「新規」を選び、検索から「emotion」と入力。Emotion API を選択します。

emo_1.png

Emotion API を選択して、作成ボタンをクリックします。

emo_2.png

各設定項目を入力、選択します。

emo_3.png

Emotions API がデプロイされたら、APIキーを取得します。

emo_4.png

Emotion API の使い方は以下に詳しく記述されています。

実際のコード

先程取得したAPIキーを利用して、コードを書きます。

今回のサンプルではシンプルに

  • html5 のFile APIで、写真を取得(撮影)
  • 取得した写真を、Emotion API に送信
  • 返り値からhapinessの値を取得
  • 条件分岐で、出力するメッセージを変更

としました。Azure への画層送信やサムネイルの表示など、画像の各種処理には jQueryを使ってます。

※サンプル実装ということで、APIキーを直接html内に書く形にしましたが、APIキーが視認できる状態は危険ですのでご注意ください。第三者に勝手に使われてしまいます。

<!DOCTYPE html>
<html lang="ja">
<head>
  <title>スマイルチェッカー</title>
  <meta charset="utf-8">
  <meta content="width=device-width, initial-scale=1" name="viewport">
</head>
<body>
  <div class="container" id="container">
    <h2>スマイルチェッカー</h2>
    <div id="message"></div>
    <div id="content">
      <p><input id="fileToUpload" name="upload" type="file"></p>
    </div>
  </div>
  <script src="https://code.jquery.com/jquery-2.1.4.min.js">
  </script> 
  <script>

       var html = '';

    $(function() {

     $('input[type=file]').after('<span id=\"image\"><\/span>');

     $('input[type=file]').change(function() {

       var file = $(this).prop('files')[0];

       if (!file.type.match('image.*')) {
         $(this).val('');
         $('span').html('');
         return;
       }

       var reader = new FileReader();

       reader.onload = function() {
         var img_src = $('<br><img height=\"300\">').attr('src', reader.result);
         $('span').html(img_src);
       }
       reader.readAsDataURL(file);


         $.ajax({
           url: "https://westus.api.cognitive.microsoft.com/emotion/v1.0/recognize",
           beforeSend: function(xhrObj){
               // Request headers
               xhrObj.setRequestHeader("Content-Type","application/octet-stream");
               xhrObj.setRequestHeader("Ocp-Apim-Subscription-Key","APIキーを記述する");
           },
           type: "POST",
           data: file,
           processData: false,
       })
       .done(function(data) {

           var smileScore = data["0"].scores.happiness;

          if(smileScore > 0.99) {
            var message = "最高の笑顔です!あなたの笑顔はすべての人を幸せにすることでしょう。";
          }

          if(0.7 <= smileScore && smileScore <= 0.99) {
            var message = "良い笑顔です!あなたの笑顔はみんなをホッとさせることでしょう。";
          }

          if(smileScore < 0.7) {
            var message = "疲れているのかな?早めに睡眠を取って、明日に備えましょう。";
          }

        alert(message);

       })
       .fail(function() {
           alert("error");
       });
     });
    });
  </script>
</body>
</html>

Monacaでスマホアプリ用にアレンジする

上記のコードを元に、Monacaでスマホアプリ用に整形します。

Monacaは、スマートフォンアプリ開発のフレームワークです。

sc_7.png

ちょっとだけ Onsen UI を使いました。

<!DOCTYPE html>
<html>
<head>
  <title>スマイルチェッカー</title>
</head>
<body>
  -
  <meta charset="utf-8">
  <meta content="width=device-width, initial-scale=1" name="viewport">
  <meta content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no" name="viewport">
  <meta content="default-src * data: gap: https://ssl.gstatic.com; style-src * 'unsafe-inline'; script-src * 'unsafe-inline' 'unsafe-eval'" http-equiv="Content-Security-Policy">
  <script src="components/loader.js">
  </script> 
  <script src="lib/onsenui/js/onsenui.min.js">
  </script>
  <link href="components/loader.css" rel="stylesheet">
  <link href="lib/onsenui/css/onsenui.css" rel="stylesheet">
  <link href="lib/onsenui/css/onsen-css-components.css" rel="stylesheet">
  <link href="css/style.css" rel="stylesheet">
  <link href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta.2/css/bootstrap.min.css" rel="stylesheet">
  <div class="center">
    スマイルチェッカー
  </div>
  <div class="container" id="container">
    <div id="message"></div>
    <div id="content">
      <div class="form-group">
        <input class="form-control-file" id="diletoUpload" name="upload" type="file">
      </div>
    </div>
  </div>
  <script src="https://code.jquery.com/jquery-2.1.4.min.js">
  </script> 
  <script>


    $(function() {

     $('input[type=file]').after('<span id=\"image\"><\/span>');

     $('input[type=file]').change(function() {

       var file = $(this).prop('files')[0];

       if (!file.type.match('image.*')) {
         $(this).val('');
         $('span').html('');
         return;
       }

       var reader = new FileReader();

       reader.onload = function() {
         var img_src = $('<br><img width=\"300\">').attr('src', reader.result);
         $('span').html(img_src);
       }
       reader.readAsDataURL(file);


         $.ajax({
           url: "https://westus.api.cognitive.microsoft.com/emotion/v1.0/recognize",
           beforeSend: function(xhrObj){
               // Request headers
               xhrObj.setRequestHeader("Content-Type","application/octet-stream");
               xhrObj.setRequestHeader("Ocp-Apim-Subscription-Key","APIキーを記述する");
           },
           type: "POST",
           data: file,
           processData: false,
       })
       .done(function(data) {

           var smileScore = data["0"].scores.happiness;

          if(smileScore > 0.99) {
            var message = "最高の笑顔です!あなたの笑顔はすべての人を幸せにすることでしょう。";
          }


          if(0.7 <= smileScore && smileScore <= 0.99) {
            var message = "良い笑顔です!あなたの笑顔はみんなをホッとさせることでしょう。";
          }


          if(smileScore < 0.7) {
            var message = "疲れているのかな?早めに睡眠を取って、明日に備えましょう。";
          }

        alert(message);


       })
       .fail(function() {
           alert("error");
       });

     });

    });


  </script>
</body>
</html>

応用

今回は単純にEmotion API の「hapiness」の値だけを使って条件分岐しました。より複雑に判断するなら、angerなど、他のパラメーターも考慮して判断するのも良いかもしれません。

また、写真と同時に、一言コメントを記述して、Movable Type やmBaaS系のサービスに笑顔+コメント付きで投稿する「笑顔日記」的なサービスも面白いかも。

他にもビジネスになりそうなアイディアはいくつかあるのですが、事業化をご希望の方はご連絡ください(嘘)

Sign up for free and join this conversation.
Sign Up
If you already have a Qiita account log in.