ButtonBaseクラスに、Imageプロパティがあります。これを設定するとボタンにイメージを表示することができます。
public Image Image { get; set; }
となっています。Imageクラスは、Bitmap, Metafileの派生クラスの機能を提供する抽象基本クラスです。ImageプロパティをImageオブジェクトまたは、Bitmapオブジェクトに設定します。
ここでは、Bitmapのコンストラクタを使ってImageプロパティを設定します。
Bitmapクラスについては、後の章で詳しく解説します。コンストラクタには多数のオーバーロードバージョンがあります。ここでは、リソースとしてexeに埋め込まれたイメージファイルをImageプロパティに設定することにします。
public Bitmap ( Type type, string resource )typeには、リソースの抽出に使用するクラスを指定します。普通は、GetTypeメソッドで取得します
resourceには、リソースの名前を指定します。
リソース名は、ファイル名が"abc.bmp"をリソースとした場合、"名前空間.abc.bmp"というようになります。通常、プロジェクト名が規定の名前空間となっています。
名前はBitmapですが、ビットマップ以外の形式でも大丈夫です。
ところで、イメージファイルをリソースとしてexeに埋め込むにはどうしたらよいのでしょうか。
これは、簡単です。
1.リソースにしたいイメージファイルを用意(bmpに限らず、GIF,JPG,TIF,PNGなどでもよい) 2.ソリューション・エクスプローラで、プロジェクト名を右クリック。「追加」「既存項目」で目的のイメージファイルを選択 3.イメージファイルのプロパティで、ビルドアクションを「埋め込まれたリソース」に設定たったこれだけです。プロジェクトのプロパティで「リソース」を選択して、あれこれしてもうまくいきません。
では、サンプルのプログラムを見てみましょう。
// imgbtn01.cs
using System;
using System.Drawing;
using System.Windows.Forms;
class imgbtn01
{
    public static void Main()
    {
        Form form = new Form();
        form.Text = "猫でもわかるプログラミング";
        form.BackColor = SystemColors.Window;
        form.ClientSize = new Size(230, 230);
        MyButton mb1 = new MyButton();
        mb1.Location = new Point(10, 10);
        MyButton mb2 = new MyButton();
        mb2.Location = new Point(20 + mb1.Width, 10);
        MyButton mb3 = new MyButton();
        mb3.Location = new Point(10, 20 + mb1.Height);
        MyButton mb4 = new MyButton();
        mb4.Location = new Point(20 + mb1.Width, 20 + mb1.Height);
        form.Controls.Add(mb1);
        form.Controls.Add(mb2);
        form.Controls.Add(mb3);
        form.Controls.Add(mb4);
        Application.Run(form);
    }
}
class MyButton : Button
{
    public MyButton()
    {
        Text = "猫";
        TextAlign = ContentAlignment.TopCenter;
        Font = new Font("MS ゴシック", 30);
        ForeColor = Color.Green;
        Size = new Size(100, 100);
        BackColor = SystemColors.Control;
        Image = new Bitmap(GetType(), "imgbtn01.cat.gif");
        ImageAlign = ContentAlignment.BottomCenter;
    }
    protected override void OnMouseHover(EventArgs e)
    {
        base.OnMouseHover(e);
        ForeColor = Color.Red;
        Cursor = Cursors.Hand;
    }
    protected override void OnMouseLeave(EventArgs e)
    {
        base.OnMouseLeave(e);
        ForeColor = Color.Green;
        Cursor = Cursors.Arrow;
    }
    protected override void OnClick(EventArgs e)
    {
        base.OnClick(e);
        string str;
        int n = Parent.Controls.IndexOf(this);
        switch (n)
        {
            case 0:
                str = "左上のボタンがクリックされました";
                break;
            case 1:
                str = "右上のボタンがクリックされました";
                break;
            case 2:
                str = "左下のボタンがクリックされました";
                break;
            case 3:
                str = "右下のボタンがクリックされました";
                break;
            default:
                str = "";
                break;
        }
        MessageBox.Show(str, "猫でもわかるプログラミング",
            MessageBoxButtons.OK, MessageBoxIcon.Information);
    }
}
まずは、Mainメソッドを見てみましょう。
form.ClientSize = new Size(230, 230);と、しています。FormクラスのClientSizeプロパティは、クライアント領域のサイズを取得、または設定します。
public Size ClientSize { get; set; }
ここでは、100*100のボタンを4つ、(2列 * 2列, 各隙間を10)クライアント領域に表示する予定なので、クライアント領域のサイズは230*230にしています。その後、MyButtonクラスのインスタンスを4つ生成してControls.Addメソッドで、子供コントロールとして登録しています。
MyButtonクラスのコンストラクタを見てみましょう。
Textプロパティを設定した後、TextAlignプロパティを設定してTextを上端中央に表示するようにしています。TextAlignプロパティは、Textの表示位置を指定するものです。(TextAlignプロパティはButtonBaseクラスのvirtualメンバ)
public virtual ContentAlignment TextAlign { get; set; }
戻り値のContentAlignmentは、System.Drawing名前空間で定義されている列挙体です。
メンバと意味は次の通りです。
| メンバ | 意味 | 
|---|---|
| BottomCenter | 内容は下端中央 | 
| BottomLeft | 下端左寄せ | 
| BottomRight | 下端右寄せ | 
| MiddleCenter | 中段中央 | 
| MiddleLeft | 中段左寄せ | 
| MiddleRight | 中段右寄せ | 
| TopCenter | 上端中央 | 
| TopLeft | 上端左寄せ | 
| TopRight | 上端右寄せ | 
Imageプロパティを次のように設定しています。
Image = new Bitmap(GetType(), "imgbtn01.cat.gif");これは、リソースとしてimgbtn01名前空間で定義されているcat.gifをImageに設定しなさいという意味です。
そして、Imageの表示位置を下端中央に指定しています。
OnMouseHoverメソッドをオーバーライドして、マウスがコントロールに乗っかったときの挙動を指定しています。
具体的にはForeColorを赤に、カーソルを指型にしています。
OnMouseLeaveメソッドは、マウスがコントロールから離れた時の挙動を指定します。
このプログラムでは、ForeColorを緑にもどし、カーソルを矢印に戻しています。
OnClickメソッドをオーバーライドして、ボタンがクリックされたときの動作を指定しています。
まず、
int n = Parent.Controls.IndexOf(this);に注目してください。
Control.ControlCollection.IndexOfメソッドは、指定されたコントロールがコントロールコレクションのインデックスを返します。これにより、Controls[x]のxがわかるわけです。ここでは、自分自身がコレクションのインデックスを調べています。これで、どのボタンがクリックしたかを知ることができるわけですね。この番号により、メッセージボックスで表示する文字列を決めています。
複数のボタンがあり、一つのイベントハンドラで処理する場合、どのボタンが押されたかを知る方法はたくさんあります。このHPで紹介した以外にも多くの方法があると思われます。
では、実行結果を見てみましょう。
マウスでポイントすると、カーソルが指型に変わり、ボタンの「猫」という文字が赤色になります。
ちょっと不満なのが、マウスをクリックしたとき「猫」の文字は少し右下に移動しますが、イメージは移動しません。
Update 31/Oct/2006 By Y.Kumei