撮影した写真を分離ストレージとPicturesHUBに保存する
2012年2月13日(月)
ロジックコードを記述する
リスト4 (MainPage.xaml.vb)
Option Strict On Imports System.Xml.Linq Imports System.IO Imports System.IO.IsolatedStorage Imports System.Windows.Media.Imaging Imports Microsoft.Phone ImageInfoクラス内にWriteableBitmapクラス型のimageFileNameを定義しておきます。 Public Class ImageInfo Property imageFileName As WriteableBitmap End Class Partial Public Class DataShowPage Inherits PhoneApplicationPage Public Sub New() InitializeComponent() End Sub
ページがアクティブになった時の処理
変数storageを、ファイルとディレクトリを格納している分離ストレージ領域を表すIsolateStorageFileクラスとして宣言します。Path.CombineでImageというフォルダとimageFileList.xmlというXMLファイル名と連結します。 分離ストレージ内のファイルを表すIsolatedStorageFileStreamクラス用オブジェクト変数myStreamを用意し、IsolatedStorageFileクラスのOpenFileメソッドでImageフォルダ内のimageFileList.xmlファイルを、指定したファイルアクセスを使用して指定したモードでファイルを開きます。開いたファイルをStreamReaderで読み込みます。ReadToEndメソッドでファイルの最後まで読み取り変数readXmldoc変数に格納しておきます。 読み込んだXMLテキストをParseメソッドでXElementとして読み込みます。ImageInfoクラス型の新しいリストであるmyImageInfoオブジェクトを作成します。 Descendantsメソッドで、子孫要素であるすべての <fileName> 要素のコレクションを選択し、各要素を、変数resultに格納しながら、以下の処理を繰り返します。 Path.CombineでImageフォルダと、<fileName>要素の属性”imageFileName”の値を連結して、変数imageFilePathに格納しておきます。変数imageStorageを、ファイルとディレクトリを格納している分離ストレージ領域を表すIsolateStorageFileクラスとして宣言します。IsolatedStorageFileクラスのOpenFileメソッドでImageフォルダ内のimageFileList.xmlファイルを、指定したファイルアクセスを使用して指定したモードでファイルを開きます。WriteableBitmap型の変数imageSourceを宣言し、PictureDecoder.DecodeJpegメソッドで、開いたストリームをJPEGファイルとしてWriteableBitmapオブジェクトにデコードします。PictureDecoder.DecodeJpegメソッドはMicrosof.Phone名前空間に属しています。WriteableBitmapクラスは書き込み更新することのできるBitmapSourceを提供するクラスです。 ImageInfoクラスのimageFileNameプロパティに、読み込んだWriteableBitmapオブジェクトのimageSourceオブジェクトを指定し、AddメソッドでmyImageInfoオブジェクトに追加していきます。ListBox1のItemsSourceプロパティにmyImageInfoオブジェクトを指定します。これで、撮った画像の一覧が表示されます。 Protected Overrides Sub OnNavigatedTo(e As System.Windows.Navigation.NavigationEventArgs) Dim storage As IsolatedStorageFile = IsolatedStorageFile.GetUserStoreForApplication Dim filePath As String = Path.Combine("Image", "imageFileList.xml") Using myStream As IsolatedStorageFileStream = storage.OpenFile(filePath, FileMode.Open, FileAccess.Read) Using reader As StreamReader = New StreamReader(myStream) Dim readXmldoc As String = reader.ReadToEnd Dim doc As XElement = XElement.Parse(readXmldoc) Dim myImageInfo As New List(Of ImageInfo) For Each result In From c In doc.Descendants("fileName") Select c Dim imageFilePath As String = Path.Combine("Image", result.Attribute("imageFileName").Value) Dim imageStorage As IsolatedStorageFile = IsolatedStorageFile.GetUserStoreForApplication Using stream As IsolatedStorageFileStream = imageStorage.OpenFile(imageFilePath, FileMode.Open, FileAccess.Read) Dim imageSource As WriteableBitmap = PictureDecoder.DecodeJpeg(stream) With myImageInfo .Add(New ImageInfo With {.imageFileName = imageSource}) End With 'stream.Close() End Using Next ListBox1.ItemsSource = myImageInfo End Using End Using MyBase.OnNavigatedTo(e) End Sub
一覧の画像から任意の画像を選択した時の処理
選択された画像のIndexを引数に、SavePicturesHUBに遷移します。 Private Sub ListBox1_SelectionChanged(sender As Object, e As System.Windows.Controls.SelectionChangedEventArgs) Handles ListBox1.SelectionChanged NavigationService.Navigate(New Uri(String.Format("/SavePicturesHUB.xaml?Index={0}", ListBox1.SelectedIndex.ToString), UriKind.Relative)) End Sub End Class
SavePicturesHUB.xamlを展開して表示される、SavePicturesHUB.xaml.vbをダブルクリックしてリスト5のコードを記述します。
ロジックコードを記述する
リスト5 (SavePicturesHUB.xaml.vb)
Option Strict On Imports System.Xml.Linq Imports System.IO Imports System.IO.IsolatedStorage Imports System.Windows.Media.Imaging Imports Microsoft.Phone Imports Microsoft.Xna.Framework.Media Partial Public Class AddEyeMaskPage Inherits PhoneApplicationPage Public Sub New() InitializeComponent() End Sub Dim myIndex As Integer Dim imageName As String Dim imageFileName As String WriteableBitmapクラス型のメンバ変数、imageSourceを宣言します。 Dim imageSource As WriteableBitmap
ページがアクティブになった時の処理
DataShowPage.xamlから渡された文字データを受け取ります。文字データはNavigationContextのQueryStringにDictionary として提供されます。送信時のキーワード(この場合Index)を基に渡された文字列情報の値(myParam(“Index”))を取得します。取得した値をInteger.Parseメソッドで数値に変換し、変数myIndexに格納しておきます。 変数storageを、ファイルとディレクトリを格納している分離ストレージ領域を表すIsolateStorageFileクラスとして宣言します。Path.CombineでImageというフォルダとimageFileList.xmlというXMLファイル名と連結し、変数filePathに格納します。 分離ストレージ内のファイルを表すIsolatedStorageFileStreamクラス用オブジェクト変数myStreamを用意し、IsolatedStorageFileクラスのOpenFileメソッドでImageフォルダ内のimageFileList.xmlファイルを、指定したファイルアクセスを使用して指定したモードでファイルを開きます。開いたファイルをStreamReaderで読み込みます。ReadToEndメソッドでファイルの最後まで読み取り変数readXmldoc変数に格納しておきます。 読み込んだXMLテキストをParseメソッドでXElementとして読み込みます。DataShowPageで選択されたインデック該当する<fileName>要素の属性”imageFileName”の値を、変数imageNameに格納します。Path.CombineでImageというフォルダと、変数imageNameに格納されている画像名を連結し、imageFileNameに格納します。 変数imageStorageを、ファイルとディレクトリを格納している分離ストレージ領域を表すIsolateStorageFileクラスとして宣言します。IsolatedStorageFileクラスのOpenFileメソッドで変数imageFileNameに格納されている画像ファイルを、指定したファイルアクセスを使用して指定したモードでファイルを開きます。PictureDecoder.DecodeJpegメソッドで、開いたストリームをJPEGファイルとしてWriteableBitmapオブジェクトにデコードし、imageSource変数で参照します。PictureDecoder.DecodeJpegメソッドはMicrosof.Phone名前空間に属しています。WriteableBitmapクラスは書き込み更新することのできるBitmapSourceを提供するクラスです。Image1のSourceプロパティにimageSourceオブジェクトを指定します。DataShowPage.xamlで選択された画像が表示されます。 Protected Overrides Sub OnNavigatedTo(e As System.Windows.Navigation.NavigationEventArgs) Dim myParam As IDictionary(Of String, String) = NavigationContext.QueryString myIndex = Integer.Parse(myParam("Index")) Dim storage As IsolatedStorageFile = IsolatedStorageFile.GetUserStoreForApplication Dim filePath As String = Path.Combine("Image", "imageFileList.xml") Using myStream As IsolatedStorageFileStream = storage.OpenFile(filePath, FileMode.Open, FileAccess.Read) Using reader As StreamReader = New StreamReader(myStream) Dim readXmldoc As String = reader.ReadToEnd Dim doc As XElement = XElement.Parse(readXmldoc) imageName = doc.Descendants("fileName")(myIndex).Attribute("imageFileName").Value imageFileName = Path.Combine("Image", imageName) Dim imageStorage As IsolatedStorageFile = IsolatedStorageFile.GetUserStoreForApplication Using stream As IsolatedStorageFileStream = imageStorage.OpenFile(imageFileName, FileMode.Open, FileAccess.Read) imageSource = PictureDecoder.DecodeJpeg(stream) Image1.Source = imageSource End Using End Using End Using MyBase.OnNavigatedTo(e) End Sub
[PicturesHUBに保存]ボタンがタップされた時の処理
保存する画像のファイル名を作成します。現在の「年月日時間分秒.jpg」ファイルを作成し、変数imageFileNameに格納しておきます。 書き込みおよび更新が可能な BitmapSourceを提供する、WriteableBitmapクラス型のmyWriteableBitmap変数を宣言します。Image1で初期化された、新しいWriteableBitmapのインスタンスmyWriteableBitmapオブジェクトを作成します。WriteableBitmapクラスの第2引数には、ビットマップに特定の変換を適用するTransformを指定できますが、ここではNothingを指定します。 変数storageを、ファイルとディレクトリを格納している分離ストレージ領域を表すIsolateStorageFileクラスとして宣言します。FileExistsメソッドで、imageNameに格納されている画像ファイルが存在しているかどうかをチェックし、存在している場合は、DeleteFileメソッドで同名ファイルを削除します。 分離ストレージ内のファイルを表すIsolatedStorageFileStreamクラス用オブジェクト変数myStream変数を用意し、IsolatedStorageFile.CreateFileメソッドで、分離ストレージ内にimageFileName変数(Image\年月日時間分秒.jpgが格納されている)の持っているファイルを作成します。 Extensions.SaveJpegメソッドで、WriteableBitmapオブジェクトを、JPEGストリームにエンコードします。これは、JPEGファイルのターゲットとなる幅と高さを設定するためのパラメーターを持っています。書式は下記の通りです。 Extensions.SaveJpeg(WriteableBitmapオブジェクト,イメージデータストリーム,WriteableBitmapオブジェクトのPixelWidth, WriteableBitmapオブジェクトのPixelHeight,0(固定),0~100の間の写真の品質(70以上を指定)) ピクチャへのアクセスを提供する新しいMediaLibrayクラスのインスタンス、myLibrayを作成します。分離ストレージ内のファイルを表すIsolatedStorageFileStreamクラス用オブジェクト変数Stream変数を用意し、IsolatedStorageFile.OpenFileメソッドで、imageFileNameに格納されているJPEGファイルを、指定したファイルアクセスを使用して指定したモードで開きます。MediaLibrary.SavePictureメソッドで、ストリームオブジェクトに含まれる画像を、メディアライブラリーに保存し、その保存した画像をピクチャオブジェクトとして返します。保存した旨のメッセージを表示します。 Private Sub saveButton_Click(sender As System.Object, e As System.Windows.RoutedEventArgs) Handles saveButton.Click Dim imageFileName As String = DateTime.Now.ToString("yyyyMMddHHmmss") & ".jpg" Dim myWriteableBitmap As WriteableBitmap myWriteableBitmap = New WriteableBitmap(Image1, Nothing) Dim storage As IsolatedStorageFile = IsolatedStorageFile.GetUserStoreForApplication If storage.FileExists(imageName) = True Then storage.DeleteFile(imageName) End If Using myStream As IsolatedStorageFileStream = storage.CreateFile(imageFileName) System.Windows.Media.Imaging.Extensions.SaveJpeg(myWriteableBitmap, myStream, myWriteableBitmap.PixelWidth, myWriteableBitmap.PixelHeight, 0, 85) End Using Dim myLibray As New MediaLibrary Using Stream As IsolatedStorageFileStream = storage.OpenFile(imageFileName, IO.FileMode.Open, IO.FileAccess.Read) myLibray.SavePicture(imageFileName, Stream) MessageBox.Show("PicturesHubに保存しました。") End Using End Sub End Class
「撮影した写真を分離ストレージとPicturesHUBに保存する」サンプルプログラム
連載バックナンバー
Think ITメルマガ会員登録受付中
Think ITでは、技術情報が詰まったメールマガジン「Think IT Weekly」の配信サービスを提供しています。メルマガ会員登録を済ませれば、メルマガだけでなく、さまざまな限定特典を入手できるようになります。