.NET TIPS VS.NETで画像などのリソースを利用するには?(読込編)デジタルアドバンテージ2004/10/22 |
|
|
「TIPS:VS.NETで画像などのリソースを利用するには?(準備編)」と「(組込編)」の内容を踏まえて、本稿ではリソース・ファイル(.resourcesファイル)や画像ファイル(.gifファイルや.jpgファイルなど)を読み込む方法について解説する。
本稿の説明で使用するサンプル・プログラム(Visual Studio .NETプロジェクト)は、次のリンクからダウンロードできる。
実際にリソースを読み込むには、まず、どのリソースを読み込むのかを指定しなければならない。そのためには、リソースの名前をあらかじめ知っておく必要がある。そこで本稿では、実際の読み込み方法について解説する前に、リソースの名前について解説しておく(なおリソース名の解説は少々長くなってしまったので、もしリソース名の解説を飛ばして「読み込み方法」の解説に進む場合には、ここをクリックして「リソースの読み込み方法」へジャンプしてほしい)。
アセンブリで利用するリソース名の種類
「準備編」では、.NETアプリケーションで利用できるリソースとして、(主に)次の5種類があることを説明した。
- 外部画像ファイル
- マニフェスト・リソース
- 外部リソース・ファイル
- 埋め込みリソース
- デザイナ・リソース
これら5種類のリソースは、「外部ファイル」なのか、「埋め込みファイル」なのかで、次のように2つに分類できる。
(1)「外部ファイル(1:外部画像ファイル、3:外部リソース・ファイル)」
(2)「埋め込みファイル(2:マニフェスト・リソース、4:埋め込みリソース、5:デザイナ・リソース)」
そこで以下では、「外部ファイルのリソース名」と「埋め込みファイルのリソース名」に分けてそれぞれ説明しよう。
外部ファイルのリソース名
外部ファイルのリソース名は、リソースとなるファイルがアセンブリの外部に配置されているだけなので、埋め込みファイルと比べると単純である。基本的に、ファイルのパス名や、(「準備編」で説明したリソース編集ツール「reseditor」などを使って入力した)リソース・ファイルのリソース名(=キー名)をそのまま使えばよい。
例えば、「組込編」で配置した外部ファイル(1:外部画像ファイルと、3:外部リソース・ファイル)のリソース名は次のようになる。
■1:外部画像ファイル
外部画像ファイルのリソース名は次の表のとおり。
名前 | 値の具体例 | 説明 |
リソース名 | dotnet_design1.gif | 外部画像ファイル「dotnet_design1.gif」は、画像リソースを読み込むアセンブリ「WindowsApplication1.exe」と同じディレクトリに配置されている。よって、絶対パスだけでなく、相対パスを使うことができる。相対パスを使えば、左のようなリソース名となる。 |
外部画像ファイルのリソース名 |
■3:外部リソース・ファイル
外部リソース・ファイルのリソース名は、次の2つに分かれる。
- ルート名(ファイル名。実際のコーディングで使用するときには拡張子「.resources」は省略する)
- キー名(リソース名。reseditorにより入力した値)
リソース・ファイルで「リソース名」といえば、基本的に「キー名」を指す。ルート名は、キー名を整理・分類するための名前空間のようなものだと考えればよいだろう。
さらに、埋め込んだファイルではなく、「外部」のリソース・ファイルの場合には、これら2つのリソース名の情報以外に、次の情報が必要になる。
- ディレクトリ・パス
以上3つの情報の値を次の表にまとめた。
名前 | 値の具体例 | 説明 |
ディレクトリ・パス | . | 外部リソース・ファイル「MyResources3.resources」は、画像リソースを読み込むアセンブリ「WindowsApplication1.exe」と同じディレクトリに配置されている。 よって「ディレクトリ・パス」には、絶対パスだけでなく、相対パスを使うことができる。相対パスを使えば、このようなディレクトリ名(カレント・ディレクトリを示す「.」)となる。 |
ルート名 | MyResources3.resources | ルート名は、外部リソース・ファイル「MyResources3.resources」となる。 ※実際のコーディングでは、拡張子「.resources」を省略する必要がある。 |
キー名 (リソース名) |
dotnet_design3 | キー名は、「準備編」で説明したリソース編集ツール「reseditor」などを使って入力した値で、本稿では「dotnet_design3」という値で画像リソースをリソース・ファイルに追加している。 |
外部リソース・ファイルのリソース名 |
埋め込みファイルのリソース名
埋め込みファイルのリソース名は、先ほどの外部ファイルほど単純ではない。なぜなら、コマンドラインにより手動でリソースを埋め込んだのではなく、Visual Studio .NET(以降、VS.NET)の機能を使って自動的にリソースを埋め込んだ場合、VS.NETにより、ある命名規則に従ってリソース名が付与されるためだ。以下では、アセンブリ内に埋め込んだリソースの名前が、実際にどのようになっているのかを調べながら、その命名規則について解説する。
■VS.NETにより埋め込まれたリソースの名前の確認
次の画面は、「組込編」でアセンブリに埋め込んだファイル(2:マニフェスト・リソース、4:埋め込みリソース、5:デザイナ・リソース)のリソース名情報を列挙したものである(このプログラムは、冒頭で示したサンプル・プログラムに含まれている)。ここで、VS.NETのIDEを利用したC#(以降、Visual C#)とVS.NETのIDEを利用したVisual Basic .NET(以降、VB.NET)の画面を並べて表示しているのは、両者でリソース名が少し異なるからだ。
上の画面にあるリソース名の情報についてそれぞれ解説していこう。
■2:マニフェスト・リソース()
マニフェスト・リソースのリソース名は次の表のとおりだ。
名前 | 値の具体例 | 説明 |
リソース名 | 【Visual C#の場合】 WindowsApplication1.images.dotnet_design2.gif |
「images」フォルダの中にある画像ファイル「dotnet_design2.gif」が、マニフェスト・リソースとしてアセンブリに埋め込まれている。VS.NETプロジェクトの「既定の名前空間」は「WindowsApplication1」なので、左のようなリソース名となる。 【マニフェスト・リソースの命名規則(Visual C#)】は、次のとおり。 <既定の名前空間>.<フォルダ名>.<ファイル名> |
【VB.NETの場合】 WindowsApplication1.dotnet_design2.gif |
上記のVisual C#とまったく同じ条件で、VB.NETプロジェクトでマニフェスト・リソースを利用すると、左のようなリソース名となる。 ここで特に注意が必要なのは、VB.NETはVisual C#と異なり、リソース名にフォルダ名(本稿の例では「images」)が追加されないことである。 【マニフェスト・リソースの命名規則(VB.NET)】は、次のとおり。 <既定の名前空間>.<ファイル名> |
|
マニフェスト・リソースのリソース名 | ||
同じマニフェスト・リソースであっても、Visual C#とVB.NETとではその値が異なるため、ここでは分けて示している(以降の表でも同様)。 |
ここで特に注意すべき点は、Visual C#の場合には、リソース名にフォルダ名「images」が追加されているところだ。このように、VS.NETによりC#プロジェクトのアセンブリに対して、マニフェスト・リソースを埋め込むと、そのリソースの名前にフォルダ名が付加される(もちろんフォルダがある場合のみである)。次に紹介する「4:埋め込みリソース」も同様に、Visual C#の場合だけリソース名にフォルダ名が追加される。
なお、VS.NETプロジェクトの「既定の名前空間」(この例では「WindowsApplication1」)は、VS.NET IDEのメニュー・バーから[プロジェクト]−[<プロジェクト名>のプロパティ]を選択すると表示される[<プロジェクト名> プロパティ ページ]ダイアログで参照することができる。
■4:埋め込みリソース()
埋め込みリソースのリソース名は次の表のとおりだ。ここでは、「組込編」でアセンブリに埋め込んだMyResx4.resxファイルのみを説明し、MyResources4.resourcesファイルの方の説明は割愛する(.resxファイルは、VS.NETにより自動的に.resourcesファイルに変換される)。なお、埋め込みリソースはリソース・ファイルなので、前述の外部リソース・ファイルと同じように、リソース名が「ルート名」と「キー名」に分割される。
名前 | 値の具体例 | 説明 |
ルート名 | 【Visual C#の場合】 WindowsApplication1.resources.MyResx4.resources |
「resources」フォルダの中にある.resxファイル「MyResx4.resx」が、(.resourcesファイルに自動変換されて)埋め込みリソースとしてアセンブリに組み込まれている。VS.NETプロジェクトの「既定の名前空間」は「WindowsApplication1」なので、左のようなリソースのルート名となる。 【埋め込みリソースのルート名の命名規則(Visual C#)】は、次のとおり。 <既定の名前空間>.<フォルダ名>.<(.resourcesファイルに自動変換された後の)ファイル名> ※実際のコーディングでは、拡張子「.resources」を省略する必要がある。 |
【VB.NETの場合】 WindowsApplication1.MyResx4.resources |
上記のVisual C#とまったく同じ条件で、VB.NETプロジェクトで埋め込み・リソースを利用すると、左のようなリソースのルート名となる。 ここで特に注意が必要なのは、VB.NETはVisual C#と異なり、リソース名にフォルダ名(本稿の例では「resources」)が追加されないことである。 【埋め込みリソースのルート名の命名規則(VB.NET)】は、次のとおり。 <既定の名前空間>.<(.resourcesファイルに自動変換された後の)ファイル名> ※実際のコーディングでは、拡張子「.resources」を省略する必要がある。 |
|
キー名 (リソース名) |
【Visual C#/VB.NETで共通】 dotnet_design4 |
キー名は、「準備編」で説明したリソース編集ツール「reseditor」などを使って入力した値で、本稿では「dotnet_design4」という値で画像リソースをリソース・ファイルに追加している。キー名はVS.NETによって命名されたものではないので、Visual C#とVB.NETでの違いはない。 |
埋め込みリソースのリソース名 |
■5:デザイナ・リソース()
デザイナ・リソースのリソース名は次の表のとおりだ。
名前 | 値の具体例 | 説明 |
ルート名 | 【Visual C#/VB.NETで共通】 WindowsApplication1.Form1.resources |
Windowsフォームの新規作成で「Form1.cs/Form1.vb」と同時に生成される.resxファイル「Form1.resx」(自動的にVS.NETプロジェクトの隠しファイルになる)がデザイナ・リソースとしてアセンブリ内に自動的に埋め込まれている。デザイナ・リソースの「WindowsApplication1」は、マニフェスト・リソースや埋め込みリソースのように「既定の名前空間」ではなく、「フォームの名前空間名」であることに注意してほしい。また、「Form1」も「ファイル名」ではなく、「フォームのクラス名」であることに注意してほしい。これらにより、左のようなリソースのルート名となる。 ここで特に注目してほしいのは、Visual C#でもリソース名にフォルダ名が追加されないことである。つまり、Visual C#とVB.NETのデザイナ・リソースには、互換性があるといえるだろう。 【デザイナ・リソースのルート名の命名規則(Visual C#/VB.NET)】は、次のとおり。 <フォームの名前空間>.<(.resourcesファイルに自動変換された後の)ファイル名> ※後に説明する実際のコーディングでは、拡張子「.resources」を省略する必要がある。 |
キー名 (リソース名) |
【Visual C#/VB.NETで共通】 pictureBox1.Locked pictureBox1.Modifiers pictureBox1.DefaultModifiers $this.Name $this.Locked ……など。 |
キー名は、VS.NETが自動的に決定した値である。左に挙げたキー名の値は生成されたものの一部である。 VS.NETが生成するリソースのキー名には、次の2種類の命名規則がある。 1. <フィールド名>.<プロパティ名> 2. $this.<プロパティ名> 「$this」は、フォーム・オブジェクト自身を意味し(C#の「this」やVB.NETの「Me」キーワードと同じようなもの)、「<フィールド名>」はフォームに配置されたコントロール・オブジェクトを意味する。つまり、1つ1つの「キー(リソース)」が、オブジェクトの「プロパティ」にそれぞれ対応しているということになる。 |
デザイナ・リソースのリソース名 |
上記の表を見ると分かるように、デザイナ・リソースの場合、(埋め込みリソースと違って)Visual C#とVB.NETでリソース名がまったく同じになるので注意してほしい。
リソースの読み込み方法
リソースの読み込み方法は、リソース・ファイル(.resourcesファイル)なのか、画像ファイル(.gifファイルや.jpgファイルなど)なのかで異なる。リソース・ファイルを読み込む場合にはResourceManagerクラス(System.Resources名前空間)を使うことが基本となるが、画像ファイルではResourceManagerクラスを使用しない。
それでは、以下に具体的な読み込み方法のサンプル・プログラムを示そう(いずれもC#のサンプル・コード)。
■アセンブリの指定
埋め込みファイル(2:マニフェスト・リソース、4:埋め込みリソース、5:デザイナ・リソース)の場合、リソース読み込みの準備として、読み込みたいリソースは「どのアセンブリに埋め込まれているのか」を明示的に指定する必要がある。このアセンブリの指定には、それを示すAssemblyオブジェクト(System.Reflection名前空間)を取得することによって行う。
現在実行中のアセンブリ(本稿の例では「WindowsApplication1.exe」)を示すAssemblyオブジェクトを取得する場合には、次のようなコードを記述すればよい(ちなみにVB.NETでは「Assembly」という単語は予約語のため、「[Assembly]」のように角括弧を付けてAssemblyキーワードではなく、Assemblyクラスであるということを明示しなければならない)。
|
|
現在実行中のアセンブリのAssemblyオブジェクトを取得するサンプル・コード |
■1. 外部画像ファイル
外部画像ファイルをリソースとして読み込むには、Bitmapクラス(System.Drawing名前空間)のコンストラクタのパラメータに、画像ファイルのパス(本稿の例では、「WindowsApplication1.exe」と同じディレクトリにある画像ファイル「dotnet_design1.gif」)を指定する。次のサンプル・コードでは、画像ファイルをリソースとして読み込み、PictureBoxコントロールのImageプロパティに設定することにより、PictureBoxコントロールに画像を表示している。
|
|
外部画像ファイルのリソース読み込みを行うサンプル・コード |
■2. マニフェスト・リソース
マニフェスト・リソースを読み込むには、先ほどの「アセンブリの指定」で取得したAssemblyオブジェクトのGetManifestResourceStreamメソッドを使う。このメソッドのパラメータにリソース名(本稿の例では「WindowsApplication1.images.dotnet_design2.gif」。詳しくは前述の説明を参照してほしい)を指定して呼び出すと、それを読み出すためのStreamオブジェクト(System.IO名前空間)を取得できる。そのStreamオブジェクトを、Bitmapクラスのコンストラクタのパラメータに指定すれば、Bitmapリソースとして画像ファイルを利用できる。
|
|
マニフェスト・リソースの読み込みを行うサンプル・コード |
なお、Bitmapクラスなど画像関連クラスのコンストラクタには、次のコード例のように、Streamオブジェクトの取得を自動的に行ってくれるものも用意されている。
pictureBox2.Image = new Bitmap(thisExe.GetType(), "images.dotnet_design2.gif");
■3. 外部リソース・ファイル
外部リソース・ファイルをリソースとして読み込むには、ResourceManagerクラスのCreateFileBasedResourceManagerメソッドを呼び出せばよい。このメソッドの第1パラメータに「ルート名」(本稿の例では「MyResources3」。ルート名の拡張子「.resources」は必ず省略しなければならない)、第2パラメータに「ディレクトリ・パス」(本稿の例では、カレント・ディレクトリを意味する「.」)、第3パラメータに「null」を指定する(ルート名やキー名については、前述の説明を参照すること)。
CreateFileBasedResourceManagerメソッドを呼び出すと、その戻り値としてResourceManagerオブジェクトを取得できる。そのResourceManagerオブジェクトのGetObjectメソッドを、パラメータに「キー名」(本稿の例では「dotnet_design3」)を指定して呼び出すことで画像リソースを使用することができる。なお、GetObjectメソッドの戻り値はObject型(System名前空間)なので、適切な型にキャストする必要がある。次のサンプル・プログラムではImageクラス(System.Drawing名前空間)にキャストしている。
|
|
外部リソース・ファイルのリソース読み込みを行うサンプル・コード |
■4. 埋め込みリソース
埋め込みリソースを読み込むには、ResourceManagerクラスのコンストラクタのパラメータに、「ルート名」(本稿の例では「WindowsApplication1.resources.MyResources4」。ルート名の拡張子「.resources」は必ず省略しなければならない)と、先ほど取得した「Assemblyオブジェクト」(本稿のコード例では「thisExe」)を指定して、ResourceManagerオブジェクトを生成する。後は、マニフェスト・リソースの場合と同じように、そのResourceManagerオブジェクトのGetObjectメソッドを、パラメータに「キー名」(本稿の例では「dotnet_design4」)を指定して呼び出せばよい。具体的には次のようなコードとなる。
|
|
埋め込みリソースの読み込みを行うサンプル・コード |
■5. デザイナ・リソース
デザイナ・リソースの読み込みは、VS.NETが自動作成するコードにより行われるので、手動で読み込む処理を記述する必要はほとんどないだろう。もし手動で読み込む必要がある場合には、埋め込みリソースとまったく同じコードを記述すればよい。具体的には次のようなコードとなる。
|
|
デザイナ・リソースの読み込みを行うサンプル・コード |
リソース読み込みサンプル・プログラムの実行
以上の5種類のリソース読み込みを実装したサンプル・プログラム(本稿冒頭でダウンロードできる)を実行したのが次の画面だ。
リソースの読み込みを行うサンプル・プログラムの実行画面 |
なお、実行ファイル(.exeファイル)以外の別のアセンブリ(例えば「.dllファイル」)にあるリソースについても、ここで説明した方法で読み込むことができる。その際、上記のコードから変更が必要な個所は「アセンブリの指定」のところで、例えば「AssemblyクラスのGetAssemblyメソッド」などを使って、別のアセンブリのAssemblyオブジェクトを取得すればよい。本稿ではこれ以上詳しくは解説しないが、そのようなコードをサンプル・プログラム内にコメント・アウトした状態で含めておいたので、興味のある読者はそちらもためしてみるとよいだろう。
カテゴリ:Windowsフォーム 処理対象:リソース カテゴリ:クラス・ライブラリ 処理対象:リソース カテゴリ:Visual Studio .NET 処理対象:リソース 使用ライブラリ:ResourceManagerクラス(System.Resources名前空間) 使用ライブラリ:Assemblyクラス(System.Reflection名前空間) 使用ライブラリ:Bitmapクラス(System.Drawing名前空間) 使用ライブラリ:Streamクラス(System.IO名前空間) 使用ライブラリ:Imageクラス(System.Drawing名前空間) 使用ライブラリ:Objectクラス(System名前空間) 関連TIPS:VS.NETで画像などのリソースを利用するには?(準備編) 関連TIPS:VS.NETで画像などのリソースを利用するには?(組込編) |
|
「.NET TIPS」 |
- 第2回 簡潔なコーディングのために (2017/7/26)
ラムダ式で記述できるメンバの増加、throw式、out変数、タプルなど、C# 7には以前よりもコードを簡潔に記述できるような機能が導入されている - 第1回 Visual Studio Codeデバッグの基礎知識 (2017/7/21)
Node.jsプログラムをデバッグしながら、Visual Studio Codeに統合されているデバッグ機能の基本の「キ」をマスターしよう - 第1回 明瞭なコーディングのために (2017/7/19)
C# 7で追加された新機能の中から、「数値リテラル構文の改善」と「ローカル関数」を紹介する。これらは分かりやすいコードを記述するのに使える - Presentation Translator (2017/7/18)
Presentation TranslatorはPowerPoint用のアドイン。プレゼンテーション時の字幕の付加や、多言語での質疑応答、スライドの翻訳を行える
|
|