日曜プログラマーのためのVisual Studio 2010入門 最終回
最新機能をさりげなく使って、楽しいコンテンツを
ドラッグ&ドロップで、青山倫子さんとツーショットを撮る
2010年08月12日 09時00分更新
今回は、Silverlight 4から使用できるようになった“ドラッグ・ドロップ機能”と“ウェブカメラ”からのキャプチャー機能を使用し、倫子さんとのツーショット撮影を楽しめるコンテンツを作ってみよう。
実装したい機能は、あらかじめ用意しておいた倫子さんの写真に“手持ちの画像ファイル”や“ウェブカメラからキャプチャーした映像”を重ね合わせて表示し、合成結果を画像ファイルとして保存するものだ。カメラ付き携帯電話のフレーム撮影機能や画像編集機能の簡易版をウェブブラウザー上で実現するイメージ、と書くと分かりやすいだろうか。
なお、Silverlightのドラッグ&ドロップ機能を動作させるブラウザーとしては、Internet Explorerを推奨する。それ以外のブラウザーでは動作しない/動作に制限があるといった制約が加わるので注意したい。
ウェブカメラからのキャプチャーした画像で2ショット
早速コンテンツの画面デザインを考えてみよう。
まずはメイン画面。画像ファイルやウェブカメラからのキャプチャー画像はすべて“共通のウィンドウ”(ここでは便宜的にプレビューウィンドウと呼ぶことにする)に表示する。
そして、プレビューウィンドウ内にファイル読込みボタン、ウェブカメラキャプチャーボタン、カメラデバイス選択コンボボックスを設置というシンプルな形で良いだろう。
まずは、ウェブカメラからのキャプチャー機能を実装していく。細かい説明は省くが、ソースファイルを順を追っていけば、すぐに理解できるシンプルな作りだ。シンプルながら、様々なコンテンツに応用・流用できる基礎的なプログラムなので、ぜひ一緒に作りながら試してみてほしい。
ウェブカメラからの静止画キャプチャーは、以下の2つの手順で実現できる。
- カメラが写す映像を、リアルタイムにプレビューウィンドウに表示する
- キャプチャーボタンをクリックした時点で、そのリアルタイム映像をカメラソースからキャプチャーした静止画(スナップショット)に変更する
ステップ1:リアルタイムプレビューを実現する
最近のノートパソコンには、ネットブックなど低価格なものを含めて、ウェブカメラが搭載されているケースが多い。一方デスクトップ環境ではUSB外付けのカメラを利用することもあるし、複数台のカメラを接続して最適なモノを使い分けたいといった環境もあるだろう。
今回はこれらのカメラから、どれを使用するかプルダウンメニューを使って設定する。プルダウンメニューへのリストの受け渡しは簡単だ。
上のコードのように、CaptureDeviceConfiguration.GetAvailableVideoCaptureDevices() の値をプルダウンメニューのアイテムソース(this.camera_list.ItemsSource)に入れるだけだ。
プルダウンメニューの選択内容がユーザーにより変更された時点で、カメラへのアクセスを開始するファンクション(camera_list_SelectionChanged)を実行するようにしておく。ファンクションが実行されると、キャプチャーソースの利用を許可するか否かのダイアログボックスが表示され、ユーザーがカメラの使用許可を承認した場合に、そのキャプチャーソースへの接続が確立する。
余談だが、このキャプチャーソースへのアクセス指示は、ユーザーイベントからのみ実行可能だ。ユーザーが意識しないままキャプチャー機能が始動してしまわないようにするためだと考えられる。そのため、キャプチャーソースへのアクセス手順が、多少まどろっこしくなるが、これは決まりごとの手順として、一連の流れをまとめて覚えてしまうといいだろう。
キャプチャーソースへの接続が確立されたのち、プレビューウィンドウの背景(Background)をこのキャプチャーソースと繋げることで、簡単にリアルタイムプレビューが可能となる。
また、次の段階でスナップショット撮影するために、キャプチャーソースの準備ができたら、this.captureSource.CaptureImageCompleted にイベントハンドラを設定しよう。そこに、スナップショット撮影に成功したときに実行されるコマンドを指定しておく。ここでは(captureSource_CaptureImageCompletedが該当する)。
ステップ2:プレビューをスナップショットへ切り替える
キャプチャーボタンには以下の命令のみを記載している。
this.captureSource.CaptureImageAsync();
この命令は、ビデオデバイスに対し、静止画の撮影を指示するもの。あらかじめ設定しておいたイベントハンドラにしたがい、撮影成功後には、「captureSource_CaptureImageCompleted」ファンクションが実行される。
このファンクションでは、いままでリアルタイムプレビューを表示していたプレビューウィンドウの背景を、カメラからキャプチャーされた静止画に切り替えて表示する。
上記ステップ1とステップ2を続けて処理することで、ウェブカメラを使ったスクリーンショット撮影と、画面への表示は完成だ。
あとはあらかじめ用意しておいた画像ファイルを読み込んで、画面に表示するプログラムを組み立てていけばいい。
画像ファイルのドラッグ&ドロップ
ここで言う“ドラッグ&ドロップ機能”とは、Silverlightのコンテンツ上に、マウスでファイルなどをドラッグ&ドロップし、そのファイルやファイルリストを使った処理を実行できる機能である。
倫子カメラでは、マイドキュメントなどのフォルダから画像ファイルをドラッグし、倫子カメラのプレビューウィンドウに読み込み、位置や画像サイズを調整し、ファイルとして保存する部分までを実装している。ここでは、その肝となるドラッグ&ドロップの実装方法をざっくりと紹介しよう。
ドラッグ&ドロップ機能を有効にするには、XAMLのドラッグ&ドロップを受け付けるGridのパラメーターである「AllowDrop」を「True」にする。それだけで、ファイルをドロップした際に発生するイベントハンドラを利用できるようになる。
ここではメイン部分で、DragEventHandlerにユーザーファンクション(cameraPreviewCanvas_Drop)を割り当てておく。下の囲みを参照。
this.camera_preview_canvas.Drop += new DragEventHandler(cameraPreviewCanvas_Drop);
cameraPreviewCanvas_Drop ファンクションでは、ドロップされたイベント情報からファイル一覧を取得し、その一覧から先頭の1個のファイルを読み込ませている。ドラッグ&ドロップで渡されるファイルの一覧は1個だけでも配列に格納される。今回は画像1点だけを処理するので、先頭の1個だけを読み込むようにしている。
さらに呼び出されるloadImageFromFileファンクションでは、画像ファイルの読み込み画像サイズを調節し、プレビューウィンドウの背景に表示する処理を組み込んである。
プレビューウィンドウに“何”を表示するかが違うだけ
今回のコンテンツでは、画像の読み込み元に以下の3種類を想定している。
- ウェブカメラからのリアルタイムプレビュー
- ウェブカメラからのキャプチャー画像
- ファイルからの画像
しかし、読み込み元は違うが、最終的にプレビューウィンドウの背景を切り替える点は同じだ。その共通点に気付いてしまえば、全体が非常にシンプルで理解しやすくなるだろう。
読み込んだ背景画像の上に、あらかじめ用意しておいた倫子さんの写真を上に重ねて表示するのが今回のコンテンツのすべてと言ってもいい。ちなみに、重ねて表示する倫子さんの写真データは、人物以外の部分にアルファ(透明)情報を設定したPNGデータを用意している。
なお、今回のコンテンツでは、完成した画像の保存にオープンソースの「Image Tools」ライブラリーを使用している。このライブラリーを使うと、複雑な画像のレタッチや圧縮処理などが簡単に扱える。
ネット上には、このように色々なコンテンツ制作の手間を大幅に省ける便利なライブラリーがたくさん存在する。使わない手はない。ぜひ有効活用してほしい。
この連載の記事
-
第3回
デジタル
青山倫子さんに詩を朗読してもらおう! -
第2回
デジタル
Visual Studio 2010で始めるSilverlightコンテンツ制作 -
第1回
デジタル
制作開始! 青山倫子さんをフィーチャーしたら? - この連載の一覧へ