チェックボックスの GridView 列を追加する (C#)
このチュートリアルでは、GridView コントロールにチェック ボックスの列を追加して、複数行の GridView のより使いやすい選択方法をユーザーに提供する方法について説明します。
はじめに
前のチュートリアルでは、特定のレコードを選択ぶために GridView にラジオ ボタンの列を追加する方法を調べました。 ラジオ ボタンの列は、ユーザーがグリッドで選ぶ項目が多くても 1 つに制限されている場合に適したユーザー インターフェイスです。 ただし、ユーザーがグリッドから任意の数の項目を選択できるようにしたい場合もあります。 たとえば、Web ベースのメール クライアントでは、通常、メッセージの一覧がチェック ボックスの列と共に表示されます。 ユーザーは任意の数のメッセージを選んでから、メールの別のフォルダーへの移動や削除などのアクションを実行できます。
このチュートリアルでは、チェック ボックスの列を追加する方法と、ポストバックでオンにされたチェック ボックスを判別する方法について説明します。 具体的には、Web ベースのメール クライアントのユーザー インターフェイスによく似た例を作成します。 この例には、Products
データベース テーブル内の製品の一覧を、各行にチェック ボックスを付けて表示する、ページングされた GridView が含まれます (図 1 を参照)。 [Delete Selected Products] ボタンがクリックされたら、選ばれている製品を削除します。
図 1: 製品の行ごとにチェック ボックスが含まれます (クリックするとフルサイズの画像が表示されます)
ステップ 1: 製品情報を一覧表示するページングされた GridView の追加
チェック ボックスの列の追加について説明する前にまず、ページングをサポートする GridView での製品の一覧表示に注目しましょう。 まず、EnhancedGridView
フォルダー内の CheckBoxField.aspx
ページを開き、ツールボックスからデザイナーに GridView をドラッグして、その ID
を Products
に設定します。 次に、ProductsDataSource
という名前の新しい ObjectDataSource への GridView のバインドを選択します。 ProductsBLL
クラスを使うように ObjectDataSource を構成し、GetProducts()
メソッドを呼び出してデータを取得します。 この GridView は読み取り専用なので、[UPDATE]、[INSERT]、[DELETE] タブのドロップダウン リストを [(なし)] に設定します。
図 2: ProductsDataSource
という名前の 新しい ObjectDataSource を作成します (クリックするとフルサイズの画像が表示されます)
図 3: GetProducts()
メソッドを使ってデータを取得するように ObjectDataSource を構成します (クリックするとフルサイズの画像が表示されます)
図 4: [UPDATE]、[INSERT]、[DELETE] の各タブのドロップダウン リストを [(なし)] に設定します (クリックするとフルサイズの画像が表示されます)
データ ソースの構成ウィザードが完了すると、Visual Studio によって、製品関連のデータ フィールドに対して BoundColumns と CheckBoxColumn が自動的に作成されます。 前のチュートリアルで行ったように、ProductName
、CategoryName
、UnitPrice
の各 BoundField 以外のすべてを削除し、HeaderText
プロパティを Product、Category、Price に変更します。 値が通貨として書式設定されるように UnitPrice
BoundField を構成します。 また、スマート タグの [ページングを有効にする] チェック ボックスをオンにして、ページングをサポートするように GridView を構成します。
選んだ製品を削除するためのユーザー インターフェイスも追加しましょう。 GridView の下に Button Web コントロールを追加し、その ID
を DeleteSelectedProducts
に設定して、その Text
プロパティを「Delete Selected Products」に設定します。 この例では、データベースから製品を実際に削除するのではなく、削除された製品を示すメッセージを表示するだけにします。 これに対応するには、ボタンの下に Label Web コントロールを追加します。 その ID を DeleteResults
に設定し、Text
プロパティをクリアして、Visible
と EnableViewState
プロパティを false
に設定します。
これらの変更を行った後、GridView、ObjectDataSource、Button、Label の宣言型マークアップは次のようになるはずです。
<p>
<asp:GridView ID="Products" runat="server" AutoGenerateColumns="False"
DataKeyNames="ProductID" DataSourceID="ProductsDataSource"
AllowPaging="True" EnableViewState="False">
<Columns>
<asp:BoundField DataField="ProductName" HeaderText="Product"
SortExpression="ProductName" />
<asp:BoundField DataField="CategoryName" HeaderText="Category"
ReadOnly="True" SortExpression="CategoryName" />
<asp:BoundField DataField="UnitPrice" DataFormatString="{0:c}"
HeaderText="Price" HtmlEncode="False"
SortExpression="UnitPrice" />
</Columns>
</asp:GridView>
<asp:ObjectDataSource ID="ProductsDataSource" runat="server"
OldValuesParameterFormatString="original_{0}"
SelectMethod="GetProducts" TypeName="ProductsBLL">
</asp:ObjectDataSource>
</p>
<p>
<asp:Button ID="DeleteSelectedProducts" runat="server"
Text="Delete Selected Products" />
</p>
<p>
<asp:Label ID="DeleteResults" runat="server" EnableViewState="False"
Visible="False"></asp:Label>
</p>
少し時間を取り、ブラウザーでページを表示してみてください (図 5 を参照)。 この時点で、最初の 10 個の製品の名前、カテゴリ、価格が表示されます。
図 5: 最初の 10 製品の名前、カテゴリ、価格の一覧が表示されます (クリックするとフルサイズの画像が表示されます)
ステップ 2: チェック ボックスの列の追加
ASP.NET 2.0 には CheckBoxField が含まれるので、それを使ってチェック ボックスの列を GridView に追加できると思うかもしれません。 残念ながら、CheckBoxField はブール型のデータ フィールドを操作するように設計されているため、それはできません。 つまり、CheckBoxField を使うには、レンダリングされたチェック ボックスがオンになっているかどうかを判断するためにその値を調べる、基になるデータ フィールドを指定する必要があります。 CheckBoxField を使って、オフになっているチェック ボックスの列だけを含めることはできません。
代わりに、TemplateField を追加し、CheckBox Web コントロールをその ItemTemplate
に追加する必要があります。 次に、Products
GridView に TemplateField を追加して、最初 (左端) のフィールドにします。 GridView のスマート タグで [テンプレートの編集] リンクをクリックして、ツールボックスから ItemTemplate
に CheckBox Web コントロールをドラッグします。 この CheckBox の ID
プロパティを ProductSelector
に設定します。
図 6: ProductSelector
という名前の CheckBox Web コントロールを TemplateField の ItemTemplate
に追加します (クリックするとフルサイズの画像が表示されます)
TemplateField と CheckBox Web コントロールを追加すると、各行に チェック ボックスが含まれるようになります。 図 7 で示されているのは、TemplateField と CheckBox を追加した後のこのページをブラウザーで表示したものです。
図 7: 製品の行ごとにチェック ボックスが含まれるようになっています (クリックするとフルサイズの画像が表示されます)
ステップ 3: ポストバックでのオンにされたチェック ボックスの判別
この時点では、チェック ボックスの列はありますが、ポストバックでオンにされたチェック ボックスを判別する方法がありません。 [Delete Selected Products] ボタンがクリックされたときに、それらの製品を削除するには、オンにされたチェック ボックスを知る必要があります。
GridView の Rows
プロパティを使うと、GridView 内のデータ行にアクセスできます。 プログラムでこれらの行を反復処理して CheckBox コントロールにアクセスし、その Checked
プロパティを調べて、CheckBox がオンになっているかどうかを確認できます。
DeleteSelectedProducts
Button Web コントロールの Click
イベント用のイベント ハンドラーを作成して、次のコードを追加します。
protected void DeleteSelectedProducts_Click(object sender, EventArgs e)
{
bool atLeastOneRowDeleted = false;
// Iterate through the Products.Rows property
foreach (GridViewRow row in Products.Rows)
{
// Access the CheckBox
CheckBox cb = (CheckBox)row.FindControl("ProductSelector");
if (cb != null && cb.Checked)
{
// Delete row! (Well, not really...)
atLeastOneRowDeleted = true;
// First, get the ProductID for the selected row
int productID =
Convert.ToInt32(Products.DataKeys[row.RowIndex].Value);
// "Delete" the row
DeleteResults.Text += string.Format(
"This would have deleted ProductID {0}<br />", productID);
}
}
// Show the Label if at least one row was deleted...
DeleteResults.Visible = atLeastOneRowDeleted;
}
Rows
プロパティは、GridView のデータ行を構成する GridViewRow
インスタンスのコレクションを返します。 ここの foreach
ループでは、このコレクションを列挙します。 プログラムで GridViewRow
オブジェクトごとに row.FindControl("controlID")
を使って行の CheckBox にアクセスします。 CheckBox がオンの場合、行の対応する ProductID
値が DataKeys
コレクションから取得されます。 この演習では DeleteResults
Label に情報メッセージを表示するだけですが、実際のアプリケーションでは、代わりに ProductsBLL
クラスの DeleteProduct(productID)
メソッドを呼び出します。
このイベント ハンドラーを追加した後は、[Delete Selected Products] ボタンをクリックすると、選んだ製品の ProductID
が表示されるようになります。
図 8: [Delete Selected Products] ボタンをクリックすると、選んだ製品の ProductID
が表示されます (クリックするとフルサイズの画像が表示されます)
ステップ 4: [Check All] と [Uncheck All] ボタンの追加
ユーザーは、現在のページのすべての製品を削除したい場合、10 個のチェック ボックスを 1 つずつオンにする必要があります。 クリックするとグリッド内のすべてのチェック ボックスがオンになる [Check All] ボタンを追加して、このプロセスを簡単にできます。 [Uncheck All] ボタンも同様に役に立ちます。
2 つの Button Web コントロールをページに追加し、GridView の上に配置します。 1 つ目の ID
を CheckAll
に設定し、その Text
プロパティを「Check All」に設定します。2 つ目の ID
を UncheckAll
に設定し、その Text
プロパティを「Uncheck All」に設定します。
<asp:Button ID="CheckAll" runat="server" Text="Check All" />
<asp:Button ID="UncheckAll" runat="server" Text="Uncheck All" />
次に、分離コード クラスに ToggleCheckState(checkState)
という名前のメソッドを作成します。これを呼び出すと、Products
GridView の Rows
コレクションが列挙され、各 CheckBox の Checked
プロパティが、渡された checkState パラメーターの値に設定されます。
private void ToggleCheckState(bool checkState)
{
// Iterate through the Products.Rows property
foreach (GridViewRow row in Products.Rows)
{
// Access the CheckBox
CheckBox cb = (CheckBox)row.FindControl("ProductSelector");
if (cb != null)
cb.Checked = checkState;
}
}
次に、CheckAll
と UncheckAll
ボタン用の Click
イベント ハンドラーを作成します。 CheckAll
のイベント ハンドラーでは単に ToggleCheckState(true)
を呼び出し、UncheckAll
では ToggleCheckState(false)
を呼び出します。
protected void CheckAll_Click(object sender, EventArgs e)
{
ToggleCheckState(true);
}
protected void UncheckAll_Click(object sender, EventArgs e)
{
ToggleCheckState(false);
}
このコードでは、[Check All] ボタンをクリックするとポストバックが発生し、GridView のすべてのチェック ボックスがオンにされます。 同様に、[Uncheck All] をクリックすると、すべてのチェック ボックスがオフにされます。 図 9 では、[Check All] ボタンがクリックされた後の画面が示されています。
図 9: [Check All] ボタンをクリックすると、すべてのチェック ボックスがオンになります (クリックするとフルサイズの画像が表示されます)
Note
チェック ボックスの列を表示するとき、すべてのチェック ボックスをオンまたはオフにする方法の 1 つは、ヘッダー行のチェック ボックスを使うことです。 さらに、現在の [Check All] と [Uncheck All] の実装にはポストバックが必要です。 ただし、チェック ボックスのオンとオフを、クライアント側スクリプトで完全に行うことができ、ユーザー エクスペリエンスがいっそう速くなります。 [Check All] と [Uncheck All] にヘッダー行チェック ボックスを使う方法の詳細と、クライアント側の手法の使用に関する説明については、クライアント側スクリプトとすべてをオンにする CheckBox を使用して GridView 内のすべての CheckBox をオンにする方法に関する説明をご覧ください。
まとめ
先に進む前にユーザーが GridView から任意の数の行を選択できるようにする必要がある場合は、チェック ボックスの列を追加するのが 1 つのオプションです。 このチュートリアルで見たように、GridView にチェック ボックスの列を含めるには、CheckBox Web コントロールを含む TemplateField を追加する必要があります。 (前のチュートリアルで行ったように、テンプレートにマークアップを直接挿入するのではなく) Web コントロールを使うと、ASP.NET はポストバックを通じてオンとオフの CheckBox を自動的に記憶します。 また、プログラムにより、コードで CheckBox にアクセスして、特定の CheckBox がオンかどうかを判断したり、オン状態を変更したりすることもできます。
このチュートリアルと最後のものでは、GridView に行セレクター列を追加する方法を見ました。 次のチュートリアルでは、少しの作業で GridView に挿入機能を追加する方法を調べます。
プログラミングに満足!
著者について
Scott Mitchell 氏は、ASP/ASP.NET に関する 7 冊の本の著者であり、4GuysFromRolla.com の設立者でもあります。1998 年以降、Microsoft の Web テクノロジを活用した業務を行っています。 Scott は、独立したコンサルタント、トレーナー、ライターとして働いています。 彼の最新の本は サムズは24時間で2.0 ASP.NET 自分自身を教えています。 にアクセスするか、ブログを使用して にアクセスmitchell@4GuysFromRolla.comできます。これは でhttp://ScottOnWriting.NET見つけることができます。