顔写真のタグにラベル情報を追加する

前回の記事ではface.com APIを利用して写真から顔の位置などの情報を検出する方法について紹介した。それにはAPIで提供されるfaces.detectメソッド(JavaScriptライブラリのfaces_detectメソッド)を利用した。今回は検出した写真に対してラベルを付加した上で、face.comのデータベースに登録する方法を解説する。このプロセスをface.comでは"トレーニング"と呼んでいる。

顔情報を保持するタグに新たにラベルの追加を行うためには、faces.detectメソッドの結果に含まれる「タグID」が必要となる。タグIDはタグを識別するための一意なIDであり、最初にdetectした際にはタグには「TEMP」から始まる仮のIDが付けられている。facesdetectメソッドを用いてタグIDを取得するコード例を以下に示す。detectResultはfacesdetectのコールバック関数であり、ここに渡されるJSONデータからタグIDを取得している。

リスト1

         var api = new Face_ClientAPI("取得したAPIキー");

         // 顔を検出
         function faceDetect() {
           var url = "画像ファイルのURL"
           api.faces_detect(url, detectResult);
         }

         // 検出したタグ情報からタグIDを取得
         function detectResult(urls,jsData) {
           var photos = jsData.photos;
           var tags = photos[0].tags;
       var tagid = tags[0].tid;
       alert(tagid);
         }

タグに対するラベル情報の追加はtagssaveメソッドを利用して行う。tagssaveメソッドの第1引数には、次のコード例のようにして対象となるタグID、ユーザID、そして任意のラベルを含むオブジェクトを渡す。ユーザIDは「ユーザ名@名前空間」という形式で表されるIDである。face.com APIではアカウントごとに2つまで独自の名前空間を登録することができる。名前空間の登録は公式サイトのAPIキーのページより行う。デフォルトではユーザ名と同じ名前の名前空間が登録されているはずだ。例えばユーザ名が"sugiyama"、名前空間が"mj.jp"であれば、ユーザIDは"sugiyama@mj.jp"となる。

なおFacebookやTwitterのアカウントを使う場合にはそれぞれ個別の認証情報が必要となる。詳細はAPIドキュメントを参照していただきたい。

リスト2

     // ラベル情報の追加
     function saveTag() {
       var tid = "取得したタグID"
       var uid = "ユーザID"
       var label = "任意のラベル"

       api.tags_save({ tids: tid, uid: uid, label: label }, saveTagResult);
     }

     // tags_saveのためのコールバック関数
     function saveTagResult(jsData) {
       alert(jsData.message + "\nstatus: " + jsData.status);
     }

この例のsaveTagResultはtags_saveのためのコールバック関数であり、ここに渡されるJSONデータのstatusプロパティの値が"success"であればタグ情報の保存が成功したということである。

tagssaveメソッドでタグ情報を保存できたら、facestrainメソッドを用いてトレーニングを実施する。このメソッドは指定されたユーザIDによって保存されているタグ情報をface.comのデータベースに登録するという処理を行う。aces_trainメソッドには、次の例のように第1引数にユーザIDと名前空間を含むオブジェクトを渡す。trainingResultメソッドはコールバック関数であり、ここに渡されるJSONデータのstatusプロパティの値が"success"であればトレーニングが成功したということだ。

リスト3

     // トレーニング
     function training() {
       var uid = "ユーザID";
       var namespace = "名前空間"

       api.faces_train({ uids: uid, namespace: namespace }, trainingResult);
     }

     // faces_train()のためのコールバック関数
     function trainingResult(jsData) {
       alert(jsData.status);
     }

以上を踏まえて、顔の検出からトレーニングまでの一連の作業を行うHTMLおよびJavaScriptの例を以下のように作成した。

リスト4

<html>
  <head>
    <meta http-equiv="content-type" content="text/html;charset=utf-8">
    <title>Face.comを使った顔認識のサンプル</title>
    <script type="text/javascript" src="api_client.js"></script>
    <script type="text/javascript">

      <!--
     var api = new Face_ClientAPI("取得したAPIキー");

     // 顔を検出
     function faceDetect() {
       var url = document.getElementById("url").value;
       api.faces_detect(url, detectResult);
     }

     // 検出したタグ情報からタグIDを取得してフォームに追加
     function detectResult(urls,jsData) {
       document.getElementById("image").innerHTML = "<img src='" + urls + "' height='250' />";

       var photos = jsData.photos;
       var tags = photos[0].tags;
       document.getElementById("tidInput").value = tags[0].tid;
     }

     // タグの保存(ラベル情報の追加)
     function saveTag() {
       var tid = document.getElementById("tidInput").value;
       var uid = document.getElementById("uidInput").value;
       var label = document.getElementById("labelInput").value;

       api.tags_save({ tids: tid, uid: uid, label: label }, saveTagResult);
     }

     // tags_save()のためのコールバック関数
     function saveTagResult(jsData) {
       alert(jsData.message + "\nstatus: " + jsData.status);
     }

     // トレーニング
     function training() {
       var uid = document.getElementById("uidInput").value;
       var namespace = document.getElementById("namespaceInput").value;

       api.faces_train({ uids: uid, namespace: namespace }, trainingResult);
     }

     // faces_train()のためのコールバック関数
     function trainingResult(jsData) {
       alert(jsData.status);
     }
// -->

    </script>
  </head>

  <body>
    <h1>Face.comを使った顔認識のサンプル</h1>

    <h2>1. 顔の検出</h2>
    <form name="detectForm">
      URL: <input id="url" type="input"  size="100"/><br/>
      <input type="button" value="顔写真を調べる" onClick="faceDetect()"><br/>
    </form>

    <div id="image"></div>

    <h2>2. タグにラベルを追加</h2>
    <form name="addForm">
      タグID: <input id="tidInput" type="input"  size="100"/><br/>
      ユーザID: <input id="uidInput" type="input"  size="30"/>
      ラベル: <input id="labelInput" type="input"  size="30"/><br/>
      <input type="button" value="タグを追加" onClick="saveTag()"><br/>
    </form>

    <h2>3. トレーニングを実施</h2>
    <form name="trainingForm">
      ユーザID: <input id="uidInput" type="input"  size="30"/>
      ネームスペース: <input id="namespaceInput" type="input"  size="30"/><br/>
      <input type="button" value="トレーニング" onClick="training()"><br/>
    </form>

  </body>
</html>

これを任意のWebサーバにアップロードしてWebブラウザからアクセスすると、最初は図1のように表示される。

図1 face.com APIを用いてトレーニングを行う例

ここで[URL]の部分に任意の顔写真のURLを指定して[顔写真を調べる]をクリックすれば、図2のように検出した顔のタグIDが[タグID]のフィールドに記入される。顔が検出できなかった場合にはタグIDには何も入力されないので、他の写真で試す必要がある。face.com APIには自分でタグを登録する方法も用意されているが、今回は省略する。

図2 タグIDが取得できたら、ユーザIDとラベルを記入して[タグを追加]ボタンをクリックする

ラベルの追加にはタグID以外にユーザIDとラベルを指定する必要があるので、それぞれをフィールドに入力して[タグを追加]ボタンをクリックする。タグ情報の保存に成功すれば図1.7のようなダイアログが表示される。

図3 タグ情報の保存に成功

続いてトレーニングを行う。この時点ではすでにtags_saveメソッドが完了しているので、図4のようにユーザIDと名前空間を記入して[トレーニング]ボタンをクリックする。トレーニングが成功すれば図5のようにダイアログに"success"と表示される。

図4 ユーザIDと名前空間を記入してトレーニングを実行する

図5 トレーニングに成功

API Sandboxでは各メソッドを任意の名前空間を指定して実行こともできるので、これを使えばトレーニングの結果を確認することが可能だ。ただし、その場合は左部の[Application]の項目に、その名前空間を利用できるアプリケーション名(APIキーを取得済みのアプリケーション名)を指定する必要がある。faces.detectメソッドを実行すれば、図6のように顔写真に指定したラベルが付けられているのが確認できる。

図6 指定したラベルが追加されている