Daydream : AndroidのDaydreamアプリをProcessing.jsで作成する

Android 4.2から搭載された新機能「Daydream」は、電源接続時やDock接続時に有効になるスクリーンセーバー機能です。

個人的にはProcessingのような「絵画的」作品が作成しやすいフレームワークでは、その制作物はスクリーンセーバーとか、壁紙のような使い方が合っていると思っているので、Daydream対応は「これぞ!」という第一印象を持ちました。

Processing界隈では、AndroidへExportされたコードがPAppletというProcessing関連のFWになるクラスに依存していて、それがActivityベースなのでLive Wallpaperが作れない…というスレッドがあったりして、通常アプリ以外のAndroidアプリを作ることがなかなか難しい背景があります。

今回はProcessingのJavaコードをなんとかするのではなく、Processing.jsの方で作品を作ってそれをDaydreamで使う方法を試してみました。

Processing.jsで作品を作る

Processing.jsの公式サイトは、Processing本家とは別にあります。

Processing.js

詳細やProcessing.min.jsなどは、この本家サイトを参照してください。
以前のエントリーでブログにProcessing作品を貼り付ける方法を記載しましたが、これがまさにProcessing.jsになります。

下記のようなタグと、script内にProcessing.jsのコードを書くことで実行できます。

<script type="text/javascript" src="processing.min.js"></script>
<script type="text/processing" data-processing-target="processing-canvas">

    /* code */

</script>
<canvas id="processing-canvas"></canvas>

他にも動的にCanvasとScriptをひもづける方法があるようで、

<canvas id="processing-canvas"></canvas>

<script type="text/javascript" src="processing.min.js"></script>
<script>
    window.onload = function() {
        var canvas = document.getElementsByTagName("canvas")[0];
        var codeElm = document.getElementById("processing-code");
        var code = codeElm.textContent || codeElm.innerHText;
        new Processing(canvas, code);
    }
</script>
<script type="text/processing" id="processing-code">

    /* code  */

</script>

でも実行できます。これだと、data-processing-target="processing-canvas"のような属性を使う必要はないです。

Daydream アプリケーションを作る

Daydreamアプリケーションを作るには、DreamServiceというクラスを継承する必要があります。

以下がサンプルコードです。

import android.service.dreams.DreamService;

public class ProcessingView extends DreamService {
    @Override
    public void onAttachedToWindow() {
        super.onAttachedToWindow();
        setInteractive(false);
        setFullscreen(true);
        setContentView(R.layout.main);
    }
}

さらに、AndroidManifext.xmlで定義を追加します。

    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >
      <!-- start -->
      <service
          android:name=".ProcessingView"
          android:icon="@drawable/ic_launcher"
          android:label="@string/app_name">
          <intent-filter>
              <action android:name="android.service.dreams.DreamService"/>
              <category android:name="android.intent.category.DEFAULT"/>
          </intent-filter>
      </service>
      <!-- end -->
    </application>

serviceタグを追加しています。 なおAndroid 4.2から対応なので、minSdkVersionは17が必須です。注意してください。

詳細は、本家や他の解説サイトに譲りますが、基本的にはこれでSetting > Display > Daydreamにアプリが表示されて、選択できるようになります。

Daydreamアプリケーションは起動条件が通常のアプリとは異なるので、セカイフォンの例などいろいろと紹介があるので、興味のある方は検索してみてください。

WebViewでProcessing.jsのコードを実行する

あとは、Processing.jsをDaydreamアプリに入れていくだけです。

先ほど作成したProcessing.jsの作品をassets以下にprocessing.min.jsと共にコピーして、WebViewを追加します。

import android.service.dreams.DreamService;
import android.webkit.WebView;

public class ProcessingView extends DreamService {
    @Override
    public void onAttachedToWindow() {
        super.onAttachedToWindow();
        setInteractive(false);
        setFullscreen(true);

        WebView webView = new WebView(this);
        webView.getSettings().setJavaScriptEnabled(true);
        setContentView(webView);        
        webView.loadUrl("file:///android_asset/processing/index.html");
    }
}

駆け足でしたが、ひとまずこれでDaydreamアプリとしてProcessing.jsの作品が実行できました。
本当は以前作成した、Angular Clockも対応したいのですがProcessing.jsだと、Processing PDE作品をフルスクリーンにする方法が見当たらず、、、右往左往しています。