--- title: Chromecastにキャストするサンプルアプリ作ってみた for Android tags: Android ChromeCast GoogleCastSDK HTML5 author: KazuyukiEguchi slide: false --- Chromecastがいよいよ日本で発売されました。 スマホやChromeブラウザから、画面出力するだけでしょ?と思っている人が結構多いと思うのですが、それは、Miracastの役割でして、Chromecastは、Chromecastがインターネットにアクセスして、コンテンツを表示するのが、本来の役割です。 Android端末から、Chromecastに命令を出して、Web上のコンテンツを表示するサンプルコードを作ってみました。(エラー処理とか基本無視ですwww) ここでは、自由にカスタマイズできるCustom Receiverを使ったものです。 試す為には、Google Cast SDK Developer契約(5ドル)払わなくてはなりませんのであしからず。 Receiverのアプリケーションは、HTML5(HTML,CSS,Javascript)で作ります。ここでは、下記のような簡単なHTMLをWebサーバにアップロードしておきます。 ```html:mini.html Chromecastテストページ
Chromecastテストぺーじだよ〜〜〜ん
``` [Google Cast SDK Developer Console](https://cast.google.com/publish/)上では、mini.htmlを置いたサイトのURLを記述します。 ![140605-0001.png](https://qiita-image-store.s3.amazonaws.com/0/33220/47b5c658-4d47-37ea-62db-b11b1b69a3f1.png) ここで、Custom Receiverを選択して ![140605-0002.png](https://qiita-image-store.s3.amazonaws.com/0/33220/25279625-d388-cc5a-5fe9-0a991ec6ebf8.png) Applecation IDが発行されるので、Android側のソースコードにこのApplication IDを記述することになります。 コンテンツの準備ができたということで、次は、Android側の準備をすることになります。 Android SDK Managerで、ライブラリを追加します。 必要なのは Android Support Library Google Play Services の2つです。 ![140605-0003.png](https://qiita-image-store.s3.amazonaws.com/0/33220/f5dcc756-57fd-2f0c-cefe-70e18973c305.png) インストールすると、Android SDKのフォルダのextrasにインストールされるので、Eclipseでインポートします! importするライブラリは2つです。 android-support-v7-mediarouter google-play-services_lib ![140605-0004.png](https://qiita-image-store.s3.amazonaws.com/0/33220/137e0c61-1c9d-fc43-5af4-88337852f9f3.png) ![140605-0005.png](https://qiita-image-store.s3.amazonaws.com/0/33220/4e236f2c-ca9c-ca07-f364-c3983c642f58.png) ![140605-0006.png](https://qiita-image-store.s3.amazonaws.com/0/33220/64cbec0b-cdd4-b143-6e23-059bcd81d4eb.png) android-support-v7-mediarouterをインポートした際にエラーが出る場合がありますので、その時は、プロジェクトのプロバティで、app_compact_v7のライブラリのパスを修正してください。 ![140605-0007.png](https://qiita-image-store.s3.amazonaws.com/0/33220/276234ff-cf27-4ccd-9c50-0bea842d421c.png) これで、新規にプロジェクトを作って開発を始められます。 新規プロジェクトを作ったら、そのプロジェクトにライブラリーを追加します。 ![140605-0008.png](https://qiita-image-store.s3.amazonaws.com/0/33220/8295dbbe-c1cb-5dd5-c565-d9490e4257a5.png) これが終わったら、今度は、Manifestファイルの設定を変更します。 Applicationタグで、Google ServiceのAPIを使うので、metaタグを追加します。 ![140605-0009.png](https://qiita-image-store.s3.amazonaws.com/0/33220/cc7e5497-4240-757b-52a9-f95c58eec14a.png) 次に、Parmissionです。 Wifiで通信しますので、INTERNETのパーミッションを追加します。 ![140605-0010.png](https://qiita-image-store.s3.amazonaws.com/0/33220/6c32a870-522a-9851-64b8-3b49185190b4.png) Google Playにアップするなら、もっと必要ですが、動作確認には、これで十分でしょう。 ```java:MainActivity.java package com.example.castcast; import com.google.android.gms.cast.CastMediaControlIntent; import android.app.Activity; import android.os.Bundle; import android.support.v7.media.MediaRouteSelector; import android.support.v7.media.MediaRouter; import android.support.v7.media.MediaRouter.RouteInfo; import android.util.Log; public class MainActivity extends Activity { private String TAG = "test"; // Google Cast SDK Developer Consoleから取得した Application IDを設定してください private static String APPLICATION_ID = "hogehoge"; // Chromecastを探索するのに使う変数類 private MediaRouter mRouter; private MediaRouteSelector mMediaRouteSelector; private MediaRouter.Callback mCB; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); // Chromecastを探す準備 mRouter = MediaRouter.getInstance(this); mMediaRouteSelector = new MediaRouteSelector.Builder().addControlCategory(CastMediaControlIntent.categoryForCast(APPLICATION_ID)).build(); mCB = new MediaRouter.Callback() { @Override public void onRouteAdded(MediaRouter router, RouteInfo route) { Log.d(TAG,"onRouteAdded=" + route.getName()); } @Override public void onRouteRemoved(MediaRouter router, RouteInfo route) { Log.d(TAG,"onRouteRemoved" + route.getName()); } }; } @Override protected void onResume() { super.onResume(); // Chromecastを探す mRouter.addCallback(mMediaRouteSelector, mCB,MediaRouter.CALLBACK_FLAG_PERFORM_ACTIVE_SCAN); } @Override protected void onPause() { if (isFinishing()) { mRouter.removeCallback(mCB); } super.onPause(); } } ``` これだけのソースで、同一ネットワークに接続されているChromecastのリストを取得することができます。 実行例Logcat出力 ![140605-0011.png](https://qiita-image-store.s3.amazonaws.com/0/33220/1356bdbf-0202-b11b-20ed-7fdc5c257340.png) デバイスが見つかったら、接続を行います。 ```java:MainActivity.javaの抜粋 // 最初に見つけたデバイスに接続を行う。 if(mSelectedDevice == null) { mSelectedDevice = CastDevice.getFromBundle(route.getExtras()); Cast.CastOptions.Builder apiOptionsBuilder = Cast.CastOptions.builder(mSelectedDevice, mCastClientListener); apiOptionsBuilder.setVerboseLoggingEnabled(true); mApiClient = new GoogleApiClient.Builder(getBaseContext()) .addApi(Cast.API, apiOptionsBuilder.build()) .addConnectionCallbacks(mConnectionCallbacks) .addOnConnectionFailedListener(mConnectionFailedListener) .build(); mApiClient.connect(); } ``` その他必要なコードは下記の通りです。 ```java:MainActivity.java抜粋 // Chromecastに接続確認用コールバック private GoogleApiClient.ConnectionCallbacks mConnectionCallbacks = new GoogleApiClient.ConnectionCallbacks() { @Override public void onConnected(Bundle connectionHint) { Log.d(TAG,"onConnected"); try { Cast.CastApi.launchApplication(mApiClient, APPLICATION_ID, false) .setResultCallback(new ResultCallback() { @Override public void onResult(ApplicationConnectionResult result) { Status status = result.getStatus(); if (status.isSuccess()) { mSessionId = result.getSessionId(); Log.d(TAG,"mSessionID=" + mSessionId); } } }); } catch(Exception ex) { Log.d(TAG,ex.toString()); } } @Override public void onConnectionSuspended(int cause) { } }; // Chromecastに接続失敗した場合に呼ばれる private GoogleApiClient.OnConnectionFailedListener mConnectionFailedListener = new GoogleApiClient.OnConnectionFailedListener() { @Override public void onConnectionFailed(ConnectionResult result) { } }; // Chromecastとの接続を解除する private void peardown() { if (mApiClient != null) { if (mApiClient.isConnected()) { try { Cast.CastApi.stopApplication(mApiClient, mSessionId); } catch (Exception e) { Log.e(TAG, "Exception while removing channel", e); } mApiClient.disconnect(); } mApiClient = null; mSelectedDevice = null; mSessionId = null; } } ``` GitHubに動くプロジェクトファイル一式([SampleCast](https://github.com/KazuyukiEguchi/SampleCast))をアップデートしてありますので、必要に応じてご利用ください。 以上、ハッピーキャスティング!