Entry search

第12回 日記アプリケーションを作る ―その8 画像読み込み機能の実装

さて、ここまでで基本機能が実装がだいぶ進んでようやく日記アプリケーションらしくなってきた。が、まだ入力画面の右上のPictureBoxコントロールがぽっかりと取り残されている。もちろん画像を取り込む機能は必須というわけではないが、せっかくだから今回は画像ファイルの読み込みと保存をする機能を追加していこう。

しくみを考える

今回は、入力画面にかかわる画像関連の機能を実装する。では画像を扱うための機能を考えてみよう。

ファイルを読み込むための処理

  • 「画像」メニューを押すと「ファイルを開く」ダイアログが表示されて画像を選択できる
  • 画像を選択したら右上のPictureBoxに表示される
  • 保存する際には画像ファイルを日記ファイルと同じ場所に、日記ファイルと同じ名前で保存する(保存形式はJPEG)

ファイルを表示するための処理

  • 日記ファイルを開くときに同名の画像ファイルがある場合には読み込んでPictureBoxに表示する

ということで、今回扱うキーポイントは以下のようになる。

  • 画像ファイルの読み込み
  • 画像ファイルの表示
  • 「ファイルを開く」ダイアログの使い方
  • 画像を指定形式で保存する方法

画像ファイルを開くための処理

まずは、画像ファイルを開くための機能を実装しよう。はじめは「ファイルを開く」ダイアログの使い方だ。

このダイアログはこれまでいろいろなアプリケーションで見て使ってきただろう。これをアプリケーションに実装するためのコントロールとして、「FileOpenDialog」コントロールが用意されている。

まずは、入力画面(editForm)のデザイン画面を開こう。そうしてツールボックスからOpenFileDialogコントロールをフォームにドラッグ&ドロップする。

01s.png

すると、フォームにはコントロールは現れずに画面下に「OpenFileDialog1」コントロールが表示される。OpenFileDialogコントロールは呼ばれるまで表示する必要がない「デバイス コンポーネント」なのでこのようになる。

では、続けてこのOpenFileDialogコントロールの設定を「プロパティ」から行なっていこう。

コントロール 項目 内容
OpenFileDialog1 Filter 画像ファイル|*.bmp; *.jpg; *.gif; *.png|すべてのファイル|*.*

これはわかりやすいだろう。ファイルを開くダイアログを表示した際に、どのファイルを表示するかを指定したファイルのフィルタである。基本的には
 表示するメッセージ|*.拡張子1; *.拡張子2・・・
のパターンを「|」を区切り記号にして記述してやればよい。
テキストファイル|*.txt; *.doc; |設定ファイル|*.ini|すべてのファイル|*.*
というのもよくあるパターンだ。

続いてファイルを開くダイアログを表示してファイルを読み込む処理を実装しよう。「画像」メニューをダブルクリックして以下のコードを実装しよう。コメント部分は入力しなくてもよい。

    Private Sub pictureMenu_Click(ByVal sender As System.Object, …
' ダイアログの戻り値用の変数 Dim ret As Windows.Forms.DialogResult ' ファイルを開くダイアログの表示 ret = Me.OpenFileDialog1.ShowDialog() ' ダイアログの終了方法のチェック If ret = Windows.Forms.DialogResult.OK Then Dim bmp As System.Drawing.Bitmap ' ファイルパスからビットマップの作成 bmp = New System.Drawing.Bitmap(OpenFileDialog1.FileName) ' PictureBoxに画像を表示 Me.contentPicture.Image = bmp End If End Sub

はじめに「ファイルを開くダイアログ」をShowDialog関数で表示する。そしてユーザーが何かファイルを選択して「OK」を押すか「Cancel」を押すかしないと、次の処理には進まない。

この時点で、文字ユーザーがファイルを指定した場合はOpenFileDialogの中に開いたファイルのファイルパスが保存される。

さて、ダイアログを表示して、Cancelされてしまったときには画像読み込みの処理をする必要がないので、ファイルを選択してOKボタンを押したかどうかチェックしている。OKの場合はファイルパスを元に(画像を読み込んで)Bitmapオブジェクトを作成する。そして、できあがった画像をPictureBoxコントロール(contentPicture)に格納するという手順である。

読み込みテストをしてみよう

では実際にテストをしてみよう。F5キーで実行したら、メニューから新規作成を選んでみよう。今日の日付の新しい日記が開いたら、右ソフトキーの「画像」メニューを押してみよう。見慣れた「ファイルを開く」ダイアログが開いて、ファイルの種類もプロパティで設定したように「画像ファイル」と「すべてのファイル」の両方が選択できるようになっている。

02s.png

ここで、適当な画像ファイルを選択してみよう。するとファイルから画像が読み込まれて画面上に表示されることが確認できる。

03s.png

画像保存処理

では今度は、画像を保存する処理を追加しよう。すでに日記を保存する処理は実装されているのでそこに、画像を保存する処理も追加する。

まず、保存するためには保存するファイルのパスを作る必要があるので、ちょっとこれまで実装したファイルを修正してみよう。

はじめに入力画面(editForm)のデザイン画面を表示し、「保存」ボタンをダブルクリックしてコードを表示する。コードは以下のように書き換えよう。

    Private Function getFilePath() As String
        Dim filename As String
        filename = "\My Documents\MyDiary\"
        filename = filename + Me.editDate.Value.ToString("yyyy年MM月dd日")
        Return filename
    End Function

    Private Sub saveMenu_Click(ByVal sender As System.Object, …
        Dim filepath As String
        filepath = Me.getFilePath() + ".txt"
            :

getFilePathという関数を設定してみた。実は画像ファイルと日記の本文のテキストファイルは、拡張子以外は共通である(という仕様にした)。そのため、関数を呼び出すとこの共通部分を返してくれる関数を作ってみた。

では、今度のここの関数の下に画像ファイルを保存する処理を追加しよう。

    Private Sub saveMenu_Click(ByVal sender As System.Object, …
: End Using
filepath = Me.getFilePath() + ".jpg" If Not Me.contentPicture.Image Is Nothing Then Me.contentPicture.Image.Save( _ filepath, _ System.Drawing.Imaging.ImageFormat.Jpeg) End If Me.Close() End Sub

まずは、先ほど作ったfilename変数を利用して画像保存用のファイルパスを作成する。

そして、まずこの日記に画像があるかどうかチェックする。画像は contentPicture.Imageに格納されているはずなので、そこに画像があるかどうかは Is Nothing 関数でチェックする。ただしIfの後にNotがあるので、「もし、Imageがなくは(Is Nothing)なかった( Not )ら?」という判定をしている。

画像があったならば、ImageのSave関数で画像を保存している。このSave関数も大変便利な関数の1つである。1つめの引数は保存するパス、2つの引数は保存する画像の形式を指定してある。Jpeg/gif/png/bitmapが選択可能だ。

画像を読み込む機能

では画像を読み込む機能を修正していこう。まずはファイルのパスに関する処理である。

Private Sub editDate_ValueChanged(ByVal sender As System.Object, …
' textBox のクリア Me.titleText.Text = "" Me.contentText.Text = "" 'ファイルパスの取得 Dim filepath As String
filepath = Me.getFilePath() + ".txt"

実は、こちらでも共通処理があったので、ファイルのパスを取得するために、さきほどgetFilePath という関数を作ったのである。

では、画像ファイル読み込みのための処理を実行してみよう。

Private Sub editDate_ValueChanged(ByVal sender As System.Object, …
:
filepath = Me.getFilePath() + ".jpg" Me.Loadpicture(filepath) End Sub Private Sub loadpicture(ByVal filepath As String) If File.Exists(filepath) Then Dim bmp As System.Drawing.Bitmap bmp = New System.Drawing.Bitmap(filepath) Me.contentPicture.Image = bmp Else Me.contentPicture.Image = Nothing End If End Sub

さて、今回も関数を作ってみた。今回は値を戻さないで、ただ画像ファイルがあれば表示するだけの処理なので、サブルーチン(Sub)を使っている。

基本的にはファイルがあるかのチェックをして、もしファイルがあれば画像を読み込んで表示し、なければ消去するといったもの。

わざわざこのように関数を使ったのは、画像読み込みのプロセスが先ほど実装した処理と同じだからである。そこで先ほどの画像読み込み機能もこの関数を使うように修正しておこう。

    Private Sub pictureMenu_Click(ByVal sender As System.Object, …
' ダイアログの戻り値用の変数 Dim ret As Windows.Forms.DialogResult ' ファイルを開くダイアログの表示 ret = Me.OpenFileDialog1.ShowDialog() ' ダイアログの終了方法のチェック If ret = Windows.Forms.DialogResult.OK Then
Me.loadpicture(OpenFileDialog1.FileName) End If End Sub End Class

テスト実行

後はテストをしてみて、ファイルが作成されるか試してみよう。

  • 1.まず、すでにある日記を選んで、「メニュー」から「編集」を押す。
  • 2.日記が読み込まれたら、「画像」を押して適当な画像を選択して読み込む。
  • 3.「保存」を押して保存する。
  • 4.もう一度同じ日付の日記を選んで、「編集」を押してみる。
    今度は保存した画像を読み込んでくれる。

まとめ

今回は比較的内容が盛りだくさんであった。ファイルを開くダイアログの使い方、画像の読み書き、そして関数を作ってまとめるといった処理である。
どれもアプリケーションには必須な要素なのでしっかりと覚えていくといいだろう。

ということで、日記の入力機能はほぼ完了したので次回は閲覧画面の処理の実装を行っていくことにしよう。

<執筆者プロフィール>

高橋 忍
元は、某重工業メーカにて航空機の自動操縦システムのソフトウェア 開発に従事。 その後、マイクロソフトにて開発サポート、コンサルタントを経て、 現在はエバンジェリストとして開発者に新しい技術を紹介している。難しい技術を楽しくわかりやすく伝えるのがモットー。
http://blogs.msdn.com/shintak/

高橋 忍のブログ
http://blogs.msdn.com/shintak/default.aspx
MSDN eye: 第 8 回「Windows Mobile 開発」
http://www.microsoft.com/japan/msdn/eye/

<書籍情報>

Windows Mobile 5.0のアプリケーション開発について、もっと詳しく知りたくなったら

Windows Mobile 5.0 アプリケーション開発 Beginner's Book

Windows Mobile 5.0 アプリケーション開発 Beginner's Book

高橋 忍・著/280ページ/2色印刷/B5変形/CD-ROM付
価格3129円(税込)/ISBN4-7741-2891-0/技術評論社・刊
発売日・2006年9月22日

This article posted by staff on 2006/10/19 13:11

Track back URL

http://www.willcom-fan.com/adm/mt-tb.cgi/157

Track backs: