なんかいろいろしてみます

Apr 10, 2018 - 1 minute read - HoloLens

HoloLensとWindowsMLとCustomVisionを使って手書き認識をしてみる(データ収集編)

Windows10の次期大型バージョンアップで追加される新機能Windows Machine LearningがHoloLens RS4でも利用できるようになりました. WindowMLはAzureのサービスのCustomVisionの学習データを利用して画像認識をすることができます.

概要

今回はHoloLensで描いた手書きデータを使ってWindowsML用の学習データを作成し,CustomVisionを使って学習したデータを元にHoloLensでの手書き認識をWindowsMLで行います. 学習データの作成からMachine Learningによる学習モデルの作成,作成した学習モデルの利用までを行うことができます. 手順が多いので今回は利用ツールの説明と学習データの取得までを行います.

WindowsMLはWindows10 17123以降のInsider Previewが必要になります.まだ正式なアップデートが行われていないため利用時に注意してください.

Windows10 Insider PreviewとHoloLens RS4 PreviewのアップデートとWindowsMLについては HoloLensでWindowsMLを試してみる(サンプル実行編) を参照してください.

実行環境

  • 開発環境
    • Windows10 Insider Preview 17127
    • Windows10 SDK Insider Preview 17115
    • Visual Studio2017
    • Unity 2017.4.0f1
  • 実行環境
    • HoloLens RS4 Preview 17123

CustomVisionの説明

  • Custom Vision ServiceとはMicrosoft Azureが提供している画像認識サービスです.
  • 自前の画像を用意することで簡単に機械学習での認識,分類が行えるようになっています.
  • Azureへの登録が必要ですがCustom Visionは無料プランが利用できます.
  • https://azure.microsoft.com/ja-jp/services/cognitive-services/custom-vision-service/
  • 上記のサイトからAzureの登録とCustom Visionの利用ができるように設定し,以下の画像のような状態まで進めておいてください.(次回から利用します)
  • +

HoloLens用手書きアプリ

手書き認識サンプル動作

  • UnityでビルドしたプロジェクトファイルをVisualStudio2017で開き,ソリューションプラットフォームをx86,実行先を「Device」に変更します.
  • USBで接続したHoloLensにプロジェクトを配置し実行すると以下のように数字の手書き認識が行えます.
  • このサンプルで利用している学習済みモデルはHoloLens内で描いたデータを利用して作成したものです.

手書き認識用学習データ取得アプリ

  • サンプルのコードを修正して手書きデータを取得するアプリに変更します.
  • Unityでビルドして生成されたVisualStudioプロジェクトを開き,「PaintML.cs」を開きます.
  • コードの1行目のコメントアウトを外して

//#define ACTIVE_IMAGECAPTURE -> #define ACTIVE_IMAGECAPTURE

データ取得機能を有効にします. - この状態で再度プロジェクトをビルドしてHoloLensで実行することで,手書きしたデータを2秒おきにローカルフォルダに保存します. - 保存される手書きデータはHoloLensの視界に入っている手書きデータのみ保存するので,絵や文字を描いた後に2秒程度見つめるようにすると上手く保存できます. - 実際の処理は以下のようになっています.(WindowsMLの画像認識部分は次回説明します)

 1void Start() {
 2        TextData.text = "";
 3        TexWidth = renderTex.width;
 4        TexHeight = renderTex.height;
 5        tex = new Texture2D(TexWidth, TexHeight, TextureFormat.RGBA32, false);
 6
 7#if ACTIVE_IMAGECAPTURE
 8        StartCoroutine(SaveCaptureImage(2.0f));
 9#else
10    }
11
12void Update() {
13        if (bytes==null)
14        {
15            RenderTexture.active = renderTex;
16            tex.ReadPixels(new Rect(0, 0, TexWidth, TexHeight), 0, 0);
17            tex.Apply();
18            bytes = tex.GetRawTextureData();
19        }
20    }
21
22private IEnumerator SaveCaptureImage(float time)
23    {
24        while (true)
25        {
26            yield return new WaitForSeconds(time);
27            var now = DateTime.Now;
28            File.WriteAllBytes(Application.persistentDataPath + "\\" + now.Hour + now.Minute + now.Second + ".png", tex.EncodeToPNG());
29            bytes = null;
30        }
31    }
  • Strat()でRendererTextureからTexture2Dを作成しUpdate()でbyte形式に変換します.
  • データの保存はコルーチンによって2秒おきにローカルフォルダに保存されるようになっています.
  • RendererTextureはHoloLensの位置にあわせているためHoloLensが見ている方向の描画を保存するようになっています.

実行結果

  • 実行後HoloLensのデバイスポータルからFile explorerを開き,「LocalAppData/WindowsMLDemo_PaintRecognition/LocalState」を選択します.
  • フォルダ内に大量の画像データ(.png)があるので全部保存します.
  • こんな感じになります

学習用データの整理

  • HoloLensからダウンロードした画像データを整理します.
  • ここでは数字認識のための画像データを参考に整理を行います.
  • 整理の手順としては以下のようになります.

    1. 数字が書かれていない or 失敗しているデータを除外する
    2. 数字が書かれている画像データをフォルダに分類して分ける
  • それぞれの番号のフォルダに番号が描かれた画像ファイルを移動させます.

  • 上記の画像のように整理できたら完成です.

まとめ

  • HoloLensを使った手書き数字認識アプリのサンプルを確認できた
  • サンプルを修正して手書きデータを保存できるようになった
  • 保存されたデータをダウンロードして学習用データの整理を行った

  • 次回は作成した学習データを利用してCustomVisionによる学習と出力された学習済みモデルを再度HoloLensのWindowsMLで手書き認識させるまでを行います.