GridView にボタンを追加し、応答する (VB)

作成者: Scott Mitchell

PDF のダウンロード

このチュートリアルでは、テンプレートと GridView コントロールまたは DetailsView コントロールのフィールドの両方にカスタム ボタンを追加する方法について説明します。 特に、ユーザーがサプライヤーをページングできるようにする FormView を持つインターフェイスを構築します。

はじめに

多くのレポート シナリオでは、レポート データへの読み取り専用アクセスが含まれますが、レポートに表示されるデータに基づいてアクションを実行する機能が含まれることは珍しくありません。 通常、これには、ボタン、LinkButton、または ImageButton Web コントロールを追加し、レポートに表示される各レコードをクリックするとポストバックが発生し、サーバー側のコードが呼び出されます。 レコードごとにデータを編集および削除することが最も一般的な例です。 実際、 データの挿入、更新、削除の概要 に関するチュートリアルから見たように、編集と削除は非常に一般的であるため、GridView、DetailsView、および FormView コントロールは、1 行のコードを記述しなくてもこのような機能をサポートできます。

[編集] ボタンと [削除] ボタンに加えて、GridView、DetailsView、および FormView コントロールには、ボタン、リンク ボタン、または ImageButton を含めることもできます。このコントロールをクリックすると、カスタム サーバー側ロジックを実行できます。 このチュートリアルでは、テンプレートと GridView コントロールまたは DetailsView コントロールのフィールドの両方にカスタム ボタンを追加する方法について説明します。 特に、ユーザーがサプライヤーをページングできるようにする FormView を持つインターフェイスを構築します。 特定のサプライヤーの場合、FormView には、関連するすべての製品を廃止としてマークするボタン Web コントロールと共に、仕入先に関する情報が表示されます。 さらに、GridView には、選択したサプライヤーによって提供された製品が一覧表示され、各行には [価格の引き上げ] ボタンと [割引価格] ボタンが含まれており、クリックした場合は、製品を UnitPrice 10% 上げたり下げたりします (図 1 を参照)。

FormView と GridView の両方に、カスタム アクションを実行するボタンが含まれています

図 1: FormView と GridView の両方に、カスタム アクションを実行するボタンが含まれています (フルサイズの画像を表示する 場合はクリックします)

手順 1: ボタン チュートリアル Web ページの追加

カスタム ボタンを追加する方法を見る前に、まず、このチュートリアルに必要な ASP.NET ページを Web サイト プロジェクトに作成してみましょう。 まず、 という名前 CustomButtonsの新しいフォルダーを追加します。 次に、次の 2 つの ASP.NET ページをそのフォルダーに追加し、各ページをマスター ページに Site.master 関連付けます。

  • Default.aspx
  • CustomButtons.aspx

カスタム Buttons-Related チュートリアルの ASP.NET ページを追加する

図 2: カスタム Buttons-Related チュートリアルの ASP.NET ページを追加する

他のフォルダーと同様に、 Default.aspx フォルダーには CustomButtons セクションにチュートリアルが一覧表示されます。 ユーザー コントロールに SectionLevelTutorialListing.ascx この機能があることを思い出してください。 したがって、このユーザー コントロールを にDefault.aspx追加するには、ソリューション エクスプローラーからページのデザイン ビューにドラッグします。

SectionLevelTutorialListing.ascx ユーザー コントロールを Default.aspx に追加する

図 3: ユーザー コントロールを SectionLevelTutorialListing.ascx に追加する Default.aspx (クリックするとフルサイズの画像が表示されます)

最後に、ページをエントリとしてファイルに Web.sitemap 追加します。 具体的には、ページングと並べ替え <siteMapNode>の後に次のマークアップを追加します。

<siteMapNode
    title="Adding Custom Buttons"
    description="Samples of Reports that Include Buttons for Performing
                  Server-Side Actions"
    url="~/CustomButtons/Default.aspx">
    <siteMapNode
        title="Using ButtonFields and Buttons in Templates"
        description="Examines how to add custom Buttons, LinkButtons,
                      or ImageButtons as ButtonFields or within templates."
        url="~/CustomButtons/CustomButtons.aspx" />
</siteMapNode>

を更新した Web.sitemap後、ブラウザーを使用してチュートリアル Web サイトを表示します。 左側のメニューに、チュートリアルの編集、挿入、削除の項目が含まれるようになりました。

サイト マップにカスタム ボタンのチュートリアルのエントリが含まれるようになりました

図 4: サイト マップにカスタム ボタンのチュートリアルのエントリが含まれるようになりました

手順 2: 仕入先をListsする FormView の追加

仕入先を一覧表示する FormView を追加して、このチュートリアルを開始しましょう。 「概要」で説明したように、この FormView を使用すると、ユーザーはサプライヤーをページングし、GridView でサプライヤーによって提供される製品が表示されます。 さらに、この FormView にはボタンが含まれます。このボタンをクリックすると、すべての仕入先の製品が廃止済みとしてマークされます。 FormView にカスタム ボタンを追加する前に、まず FormView を作成してサプライヤー情報を表示します。

まず、フォルダー内の CustomButtons.aspx ページを CustomButtons 開きます。 FormView をページに追加するには、[ツールボックス] から Designer にドラッグし、そのプロパティを IDSuppliers設定します。 FormView のスマート タグから、 という名前 SuppliersDataSourceの新しい ObjectDataSource を作成することを選択します。

SuppliersDataSource という名前の新しい ObjectDataSource を作成する

図 5: 名前付きの SuppliersDataSource 新しい ObjectDataSource を作成する (クリックするとフルサイズの画像が表示されます)

クラスの GetSuppliers() メソッドからSuppliersBLLクエリを実行するように、この新しい ObjectDataSource を構成します (図 6 を参照)。 この FormView には仕入先情報を更新するためのインターフェイスが用意されていないため、[更新] タブのドロップダウン リストから [(なし)] オプションを選択します。

SuppliersBLL クラスの GetSuppliers() メソッドを使用するようにデータ ソースを構成する

図 6: クラスのGetSuppliers()メソッドを使用するようにデータ ソースをSuppliersBLL構成する (フルサイズの画像を表示する をクリックします)

ObjectDataSource を構成すると、Visual Studio によって FormView の 、EditItemTemplate、および ItemTemplate が生成InsertItemTemplateされます。 と EditItemTemplateInsertItemTemplate削除し、ItemTemplate仕入先の会社名と電話番号のみを表示するように を変更します。 最後に、スマート タグの [ページングを有効にする] チェック ボックスをオンにするか、そのプロパティを に設定して、FormView のページングのサポートをAllowPagingTrue有効にします。 これらの変更後、ページの宣言型マークアップは次のようになります。

<asp:FormView ID="Suppliers" runat="server" DataKeyNames="SupplierID"
    DataSourceID="SuppliersDataSource" EnableViewState="False" AllowPaging="True">
    <ItemTemplate>
        <h3>
            <asp:Label ID="CompanyName" runat="server"
                Text='<%# Bind("CompanyName") %>' />
        </h3>
        <b>Phone:</b>
        <asp:Label ID="PhoneLabel" runat="server" Text='<%# Bind("Phone") %>' />
    </ItemTemplate>
</asp:FormView>
<asp:ObjectDataSource ID="SuppliersDataSource" runat="server"
    OldValuesParameterFormatString="original_{0}"
    SelectMethod="GetSuppliers" TypeName="SuppliersBLL">
</asp:ObjectDataSource>

図 7 は、ブラウザーで表示されたCustomButtons.aspx ページを示しています。

FormView Lists現在選択されている仕入先の CompanyName フィールドと Phone フィールド

図 7: FormView Lists、CompanyName現在選択されている仕入先の フィールドと Phone フィールド (フルサイズの画像を表示する をクリックします)

手順 3: 選択した仕入先の製品をListsする GridView の追加

FormView のテンプレートに [すべての製品を中止する] ボタンを追加する前に、まず、選択した仕入先から提供された製品を一覧表示する FormView の下に GridView を追加します。 これを実現するには、ページに GridView を追加し、その ID プロパティを に SuppliersProducts設定し、 という名前 SuppliersProductsDataSourceの新しい ObjectDataSource を追加します。

SuppliersProductsDataSource という名前の新しい ObjectDataSource を作成する

図 8: 名前付きの SuppliersProductsDataSource 新しい ObjectDataSource を作成する (フルサイズの画像を表示する をクリックします)

ProductsBLL クラスの メソッド GetProductsBySupplierID(supplierID) を使用するようにこの ObjectDataSource を構成します (図 9 を参照)。 この GridView では製品の価格を調整できますが、組み込みの編集機能や GridView からの削除機能は使用されません。 したがって、ObjectDataSource の UPDATE、INSERT、DELETE タブのドロップダウン リストを (None) に設定できます。

ProductsBLL クラスの GetProductsBySupplierID(supplierID) メソッドを使用するようにデータ ソースを構成する

図 9: クラスのGetProductsBySupplierID(supplierID)メソッドを使用するようにデータ ソースをProductsBLL構成する (フルサイズの画像を表示する をクリックします)

メソッドは GetProductsBySupplierID(supplierID) 入力パラメーターを受け取るので、ObjectDataSource ウィザードによって、このパラメーター値のソースの入力を求められます。 FormView から値を SupplierID 渡すには、[パラメーター ソース] ドロップダウン リストを Control に、ControlID ドロップダウン リストを に Suppliers 設定します (手順 2 で作成した FormView の ID)。

supplierID パラメーターが Suppliers FormView コントロールから取得されることを示す

図 10: パラメーターが supplierID FormView コントロールから Suppliers 取得されることを示す (フルサイズの画像を表示する をクリックします)

ObjectDataSource ウィザードを完了すると、GridView には各製品のデータ フィールドの BoundField または CheckBoxField が含まれます。 これをトリミングして、 ProductNameUnitPrice BoundField を CheckBoxField と Discontinued 共に表示します。さらに、テキストが通貨として書式設定されるように BoundField の書式を設定します UnitPrice 。 GridView と SuppliersProductsDataSource ObjectDataSource の宣言型マークアップは、次のマークアップのようになります。

<asp:GridView ID="SuppliersProducts" AutoGenerateColumns="False"
    DataKeyNames="ProductID" DataSourceID="SuppliersProductsDataSource"
    EnableViewState="False" runat="server">
    <Columns>
        <asp:BoundField DataField="ProductName" HeaderText="Product"
            SortExpression="ProductName" />
        <asp:BoundField DataField="UnitPrice" HeaderText="Price"
            SortExpression="UnitPrice" DataFormatString="{0:C}"
            HtmlEncode="False" />
        <asp:CheckBoxField DataField="Discontinued" HeaderText="Discontinued"
            SortExpression="Discontinued" />
    </Columns>
</asp:GridView>
<asp:ObjectDataSource ID="SuppliersProductsDataSource" runat="server"
    OldValuesParameterFormatString="original_{0}"
    SelectMethod="GetProductsBySupplierID" TypeName="ProductsBLL">
    <SelectParameters>
        <asp:ControlParameter ControlID="Suppliers" Name="supplierID"
            PropertyName="SelectedValue" Type="Int32" />
    </SelectParameters>
</asp:ObjectDataSource>

この時点で、このチュートリアルではマスター/詳細レポートが表示されます。これにより、ユーザーは上部の FormView からサプライヤーを選択し、下部の GridView を介してそのサプライヤーから提供された製品を表示できます。 図 11 は、FormView から東京トレーダーのサプライヤーを選択するときのこのページのスクリーン ショットを示しています。

選択した仕入先の製品が GridView に表示される

図 11: 選択した仕入先の製品が GridView に表示されます (フルサイズの画像を表示する をクリックします)。

手順 4: 仕入先のすべての製品を中止する DAL メソッドと BLL メソッドを作成する

ボタンを FormView に追加する前に、ボタンをクリックすると、すべての仕入先の製品が中止されます。まず、このアクションを実行する DAL と BLL の両方にメソッドを追加する必要があります。 特に、このメソッドには という名前が付けられます DiscontinueAllProductsForSupplier(supplierID)。 FormView のボタンをクリックすると、選択した仕入先 SupplierIDを渡して、ビジネス ロジック レイヤーでこのメソッドを呼び出します。BLL は対応するデータ アクセス層メソッドを呼び出します。これにより、指定した仕入先の製品を中止するステートメントがデータベースに発行 UPDATE されます。

前のチュートリアルで行ったとおり、最初に DAL メソッドを作成してから BLL メソッドを作成し、最後に ASP.NET ページで機能を実装する、ボトムアップ アプローチを使用します。 フォルダーで Northwind.xsd Typed DataSet を App_Code/DAL 開き、 に新しいメソッドを ProductsTableAdapter 追加します (を右クリックし、[クエリの ProductsTableAdapter 追加] を選択します)。 これにより、TableAdapter クエリ構成ウィザードが表示され、新しいメソッドを追加するプロセスについて説明します。 まず、DAL メソッドがアドホック SQL ステートメントを使用することを示します。

アドホック SQL ステートメントを使用して DAL メソッドを作成する

図 12: アドホック SQL ステートメントを使用して DAL メソッドを作成する (フルサイズの画像を表示する をクリックします)

次に、作成するクエリの種類を確認するメッセージが表示されます。 DiscontinueAllProductsForSupplier(supplierID)メソッドはデータベース テーブルをProducts更新する必要があるため、指定した supplierIDによって提供されるすべての製品のフィールドを 1 に設定Discontinuedし、データを更新するクエリを作成する必要があります。

UPDATE クエリの種類を選択する

図 13: UPDATE クエリの種類を選択します (クリックするとフルサイズの画像が表示されます)

次のウィザード画面には、DataTable で定義されている各フィールドを更新する TableAdapter の既存 UPDATE のステートメントが Products 表示されます。 このクエリ テキストを次のステートメントに置き換えます。

UPDATE [Products] SET
   Discontinued = 1
WHERE SupplierID = @SupplierID

このクエリを入力して [次へ] をクリックすると、最後のウィザード画面で、新しいメソッド名の使用 DiscontinueAllProductsForSupplierが求められます。 [完了] ボタンをクリックしてウィザードを完了します。 DataSet Designerに戻ると、 という名前DiscontinueAllProductsForSupplier(@SupplierID)の に新しいメソッドがProductsTableAdapter表示されます。

新しい DAL メソッドに名前を付けますAllProductsForSupplier

図 14: 新しい DAL メソッド DiscontinueAllProductsForSupplier に名前を付ける (フルサイズの画像を表示するをクリックします)

DiscontinueAllProductsForSupplier(supplierID)データ アクセス層でメソッドを作成する次のタスクは、ビジネス ロジック層に メソッドを作成DiscontinueAllProductsForSupplier(supplierID)することです。 これを行うには、クラス ファイルを ProductsBLL 開き、次を追加します。

Public Function DiscontinueAllProductsForSupplier(supplierID As Integer) As Integer
    Return Adapter.DiscontinueAllProductsForSupplier(supplierID)
End Function

このメソッドは、指定されたsupplierIDパラメーター値をDiscontinueAllProductsForSupplier(supplierID)渡して、DAL 内の メソッドを呼び出すだけです。 特定の状況下でサプライヤーの製品の廃止のみを許可するビジネス ルールがある場合は、BLL でこれらのルールを実装する必要があります。

注意

クラスのUpdateProductオーバーロードProductsBLLとは異なり、DiscontinueAllProductsForSupplier(supplierID)メソッド シグネチャには 属性 (<System.ComponentModel.DataObjectMethodAttribute(System.ComponentModel.DataObjectMethodType.Update, Boolean)>) はDataObjectMethodAttribute含まれません。 これにより、ObjectDataSource の [データ ソースの構成] ウィザードのドロップダウン リストの [更新] タブのメソッドが除外 DiscontinueAllProductsForSupplier(supplierID) されます。この属性は省略しました。これは、ASP.NET ページのイベント ハンドラーからメソッドを直接呼び出 DiscontinueAllProductsForSupplier(supplierID) すことになるためです。

手順 5: FormView への [すべての製品の中止] ボタンの追加

DiscontinueAllProductsForSupplier(supplierID) BLL と DAL のメソッドが完了したら、選択したサプライヤーのすべての製品を中止する機能を追加する最後の手順は、FormView の ItemTemplateに Button Web コントロールを追加することです。 このようなボタンを仕入先の電話番号の下に追加し、ボタン テキストとして [すべての製品を中止する] とプロパティ値 DiscontinueAllProductsForSupplierID追加します。 このボタン Web コントロールは、FormView のスマート タグの [テンプレートの編集] リンク (図 15 を参照) をクリックするか、宣言構文を使用して直接クリックして、Designerを使用して追加できます。

FormView の ItemTemplate に [すべての製品の中止] ボタン Web コントロールを追加する

図 15: FormView に [すべての製品を中止する] ボタン Web コントロールを追加する (フルサイズのItemTemplate画像を表示する場合をクリックします)

ページにアクセスするユーザーがボタンをクリックすると、ポストバックが発生し、FormView の ItemCommand イベント が発生します。 このボタンがクリックされた場合に応答してカスタム コードを実行するには、このイベントのイベント ハンドラーを作成します。 ただし、FormView 内で ItemCommandButton、 LinkButton、または ImageButton Web コントロールがクリックされるたびにイベントが発生することを理解します。 つまり、ユーザーが FormView で 1 つのページから別のページに移動すると、 ItemCommand イベントが発生します。挿入、更新、または削除をサポートする FormView でユーザーが [新規]、[編集]、または [削除] をクリックしたときと同じことが発生します。

クリックされた ItemCommand ボタンに関係なく が起動するため、イベント ハンドラーでは、[すべての製品を中止] ボタンがクリックされたかどうか、または他のボタンであるかどうかを判断する方法が必要です。 これを実現するために、Button Web コントロールの CommandName プロパティを特定の値に設定できます。 ボタンをクリックすると、この CommandName 値がイベント ハンドラーに ItemCommand 渡され、[すべての製品を中止] ボタンがクリックされたボタンであるかどうかを判断できます。 [すべての製品を中止] ボタンの CommandName プロパティを [中止] [製品] に設定します。

最後に、クライアント側の確認ダイアログ ボックスを使用して、ユーザーが選択した仕入先の製品を本当に中止することを確認します。 「 削除時の Client-Side 確認の追加 」チュートリアルで説明したように、これは JavaScript のビットを使用して実現できます。 特に、Button Web コントロールの OnClientClick プロパティを に設定します。 return confirm('This will mark _all_ of this supplier\'s products as discontinued. Are you certain you want to do this?');

これらの変更を行った後、FormView の宣言構文は次のようになります。

<asp:FormView ID="Suppliers" runat="server" DataKeyNames="SupplierID"
    DataSourceID="SuppliersDataSource" EnableViewState="False"
    AllowPaging="True">
    <ItemTemplate>
        <h3><asp:Label ID="CompanyName" runat="server"
            Text='<%# Bind("CompanyName") %>'></asp:Label></h3>
        <b>Phone:</b>
        <asp:Label ID="PhoneLabel" runat="server" Text='<%# Bind("Phone") %>' />
        <br />
        <asp:Button ID="DiscontinueAllProductsForSupplier" runat="server"
            CommandName="DiscontinueProducts" Text="Discontinue All Products"
            OnClientClick="return confirm('This will mark _all_ of this supplier\'s
                products as discontinued. Are you certain you want to do this?');" />
    </ItemTemplate>
</asp:FormView>

次に、FormView の イベントのイベント ハンドラーを ItemCommand 作成します。 このイベント ハンドラーでは、まず [すべての製品の中止] ボタンがクリックされたかどうかを判断する必要があります。 その場合は、 クラスのインスタンスを作成し、そのDiscontinueAllProductsForSupplier(supplierID)メソッドをProductsBLL呼び出し、選択した FormView の をSupplierID渡します。

Protected Sub Suppliers_ItemCommand(sender As Object, e As FormViewCommandEventArgs) _
    Handles Suppliers.ItemCommand
    If e.CommandName.CompareTo("DiscontinueProducts") = 0 Then
        ' The "Discontinue All Products" Button was clicked.
        ' Invoke the ProductsBLL.DiscontinueAllProductsForSupplier(supplierID) method
        ' First, get the SupplierID selected in the FormView
        Dim supplierID As Integer = CType(Suppliers.SelectedValue, Integer)
        ' Next, create an instance of the ProductsBLL class
        Dim productInfo As New ProductsBLL()
        ' Finally, invoke the DiscontinueAllProductsForSupplier(supplierID) method
        productInfo.DiscontinueAllProductsForSupplier(supplierID)
    End If
End Sub

SupplierID FormView で現在選択されている仕入先の には、FormView の SelectedValue プロパティを使用してアクセスできることに注意してください。 プロパティは SelectedValue 、FormView に表示されるレコードの最初のデータ キー値を返します。 FormView の DataKeyNames プロパティは、データ キー値の取得元のデータ フィールドを示します。これは、手順 2 で ObjectDataSource を FormView に SupplierID バインドするときに、Visual Studio によって自動的に に設定されました。

イベント ハンドラーを ItemCommand 作成したら、少し時間を取ってページをテストします。 協力者デケソス 'ラスカブラス' サプライヤーを参照してください (それは私のためのFormViewの5番目のサプライヤーです). このサプライヤーは、Queso Cabrales と Queso Manchego La Pastora の 2 つの製品を提供しています。どちらも廃止 されていません

協力者デ ケソス 'ラス カブラス' が廃業したため、その製品が廃止される予定であることを想像してください。 [すべての製品を中止] ボタンをクリックします。 これにより、クライアント側の確認ダイアログ ボックスが表示されます (図 16 を参照)。

協力的なデケソスラスカブラスは2つのアクティブな製品を供給します

図 16: 協力的なデ ケソス ラス カブラス供給 2 つのアクティブな製品 (フルサイズの画像を表示する をクリックします)

クライアント側の確認ダイアログ ボックスで [OK] をクリックすると、フォームの送信が続行され、FormView の ItemCommand イベントが発生するポストバックが発生します。 作成したイベント ハンドラーが実行され、 メソッドが DiscontinueAllProductsForSupplier(supplierID) 呼び出され、Queso Cabrales と Queso Manchego La Pastora 製品の両方が廃止されます。

GridView のビューステートを無効にした場合、GridView はポストバックごとに基になるデータ ストアにリバウンドされるため、これら 2 つの製品が廃止されたことを反映するように直ちに更新されます (図 17 を参照)。 ただし、GridView でビューステートを無効にしていない場合は、この変更を行った後にデータを GridView に手動で再バインドする必要があります。 これを実現するには、 メソッドを呼び出した直後に GridView の DataBind() メソッドを DiscontinueAllProductsForSupplier(supplierID) 呼び出します。

[すべての製品を中止] ボタンをクリックすると、サプライヤーの製品は適宜更新されます

図 17: [すべての製品を中止] ボタンをクリックすると、それに応じて仕入先の製品が更新されます (フルサイズの画像を表示する をクリックします)

手順 6: 製品の価格を調整するためのビジネス ロジック レイヤーでの UpdateProduct オーバーロードの作成

FormView の [すべての製品を中止] ボタンと同様に、GridView で製品の価格を増減するためのボタンを追加するには、まず適切なデータ アクセス層とビジネス ロジック層のメソッドを追加する必要があります。 DAL には 1 つの製品行を更新するメソッドが既に存在するため、BLL の メソッドに新 UpdateProduct しいオーバーロードを作成することで、このような機能を提供できます。

過去 UpdateProduct のオーバーロードでは、製品フィールドの組み合わせをスカラー入力値として取得し、指定された製品のフィールドのみを更新しました。 このオーバーロードでは、この標準とは若干異なります。代わりに、(新しいUnitPrice調整された自体を渡すのではなく) を調整UnitPriceするための製品とProductIDパーセンテージを渡します。 この方法では、現在の製品 UnitPriceを決定する必要がないため、ASP.NET ページ分離コード クラスで記述する必要があるコードが簡略化されます。

UpdateProductこのチュートリアルのオーバーロードを次に示します。

Public Function UpdateProduct _
    (unitPriceAdjustmentPercentage As Decimal, productID As Integer) As Boolean
    Dim products As Northwind.ProductsDataTable = Adapter.GetProductByProductID(productID)
    If products.Count = 0 Then
        ' no matching record found, return false
        Return False
    End If
    Dim product As Northwind.ProductsRow = products(0)
    ' Adjust the UnitPrice by the specified percentage (if it's not NULL)
    If Not product.IsUnitPriceNull() Then
        product.UnitPrice *= unitPriceAdjustmentPercentage
    End If
    ' Update the product record
    Dim rowsAffected As Integer = Adapter.Update(product)
    ' Return true if precisely one row was updated, otherwise false
    Return rowsAffected = 1
End Function

このオーバーロードは、DAL メソッド GetProductByProductID(productID) を使用して、指定された製品に関する情報を取得します。 次に、製品に UnitPrice データベース NULL 値が割り当てられているかどうかを確認します。 その場合、価格は変更されません。 ただし、値NULLUnitPrice以外がある場合、メソッドは指定されたパーセント (unitPriceAdjustmentPercent) で製品をUnitPrice更新します。

手順 7: GridView に増減ボタンを追加する

GridView (と DetailsView) は、どちらもフィールドのコレクションで構成されます。 BoundFields、CheckBoxFields、および TemplateFields に加えて、ASP.NET には ButtonField が含まれています。この名前が示すように、各行に Button、LinkButton、または ImageButton を含む列としてレンダリングされます。 FormView と同様に、GridView ページング ボタン、編集または削除ボタン、並べ替えボタンなどのボタンをクリックすると、ポストバックが発生し、GridView の RowCommand イベントが発生します。

ButtonField には、 CommandName 指定した値を各 Buttons プロパティに割り当てるプロパティがあります CommandName 。 FormView と同様に、 CommandName 値はイベント ハンドラーによって使用され RowCommand 、クリックされたボタンが決定されます。

2 つの新しい ButtonFields を GridView に追加します。1 つはボタン テキスト Price +10% で、もう 1 つは Price -10% というテキストです。 これらの ButtonFields を追加するには、GridView のスマート タグから [列の編集] リンクをクリックし、左上のリストから ButtonField フィールドの種類を選択し、[追加] ボタンをクリックします。

GridView に 2 つの ButtonFields を追加する

図 18: GridView に 2 つの ButtonFields を追加する

2 つの ButtonFields を移動して、最初の 2 つの GridView フィールドとして表示されるようにします。 次に Text 、これら 2 つの ButtonFields のプロパティを Price +10% と Price -10% に設定し CommandName 、プロパティをそれぞれ IncreasePrice と DecreasePrice に設定します。 既定では、ButtonField はボタンの列を LinkButtons としてレンダリングします。 ただし、これは ButtonField の ButtonType プロパティを使用して変更できます。 これら 2 つの ButtonFields を通常のプッシュ ボタンとしてレンダリングしてみましょう。したがって、 プロパティを ButtonTypeButton設定します。 図 19 は、これらの変更が行われた後の [フィールド] ダイアログ ボックスを示しています。これは GridView の宣言型マークアップです。

ButtonFields Text、CommandName、ButtonType の各プロパティを構成する

図 19: ButtonFields、、CommandName、および プロパティをButtonTypeText構成する

<asp:GridView ID="SuppliersProducts" runat="server" AutoGenerateColumns="False"
    DataKeyNames="ProductID" DataSourceID="SuppliersProductsDataSource"
    EnableViewState="False">
    <Columns>
        <asp:ButtonField ButtonType="Button" CommandName="IncreasePrice"
            Text="Price +10%" />
        <asp:ButtonField ButtonType="Button" CommandName="DecreasePrice"
            Text="Price -10%" />
        <asp:BoundField DataField="ProductName" HeaderText="Product"
            SortExpression="ProductName" />
        <asp:BoundField DataField="UnitPrice" HeaderText="Price"
            SortExpression="UnitPrice" DataFormatString="{0:C}"
            HtmlEncode="False" />
        <asp:CheckBoxField DataField="Discontinued" HeaderText="Discontinued"
            SortExpression="Discontinued" />
    </Columns>
</asp:GridView>

これらの ButtonFields を作成したら、最後に GridView イベント RowCommand のイベント ハンドラーを作成します。 このイベント ハンドラーは、Price +10% または Price -10% ボタンがクリックされたために発生した場合、ボタンがクリックされた行の を決定ProductIDし、クラス s UpdateProduct メソッドを呼び出ProductsBLLし、 と共に適切なUnitPrice割合の調整をProductID渡す必要があります。 次のコードは、これらのタスクを実行します。

Protected Sub SuppliersProducts_RowCommand _
    (sender As Object, e As GridViewCommandEventArgs) _
        Handles SuppliersProducts.RowCommand
    If e.CommandName.CompareTo("IncreasePrice") = 0 OrElse _
       e.CommandName.CompareTo("DecreasePrice") = 0 Then
        ' The Increase Price or Decrease Price Button has been clicked
        ' Determine the ID of the product whose price was adjusted
        Dim productID As Integer = Convert.ToInt32( _
            SuppliersProducts.DataKeys(Convert.ToInt32(e.CommandArgument)).Value)
        ' Determine how much to adjust the price
        Dim percentageAdjust As Decimal
        If e.CommandName.CompareTo("IncreasePrice") = 0 Then
            percentageAdjust = 1.1
        Else
            percentageAdjust = 0.9
        End If
        ' Adjust the price
        Dim productInfo As New ProductsBLL()
        productInfo.UpdateProduct(percentageAdjust, productID)
    End If
End Sub

[価格 + 10%] または [価格 -10%] ボタンがクリックされた行の を決定 ProductID するには、GridView の DataKeys コレクションを参照する必要があります。 このコレクションは、GridView 行ごとに プロパティで DataKeyNames 指定されたフィールドの値を保持します。 ObjectDataSource を GridView にバインドするときに、Visual Studio によって GridView の DataKeyNames プロパティが ProductID に設定されたため、DataKeys(rowIndex).Value指定された rowIndex に 対して がProductID提供されます。

ButtonField は、 パラメーターを使用してボタンがクリックされた行の rowIndex を自動的に e.CommandArgument 渡します。 したがって、Price +10% または Price -10% ボタンがクリックされた行の を決定 ProductID するには、 を使用します Convert.ToInt32(SuppliersProducts.DataKeys(Convert.ToInt32(e.CommandArgument)).Value)

[すべての製品を中止] ボタンと同様に、GridView のビューステートを無効にした場合、GridView はポストバックごとに基になるデータ ストアにリバウンドされるため、いずれかのボタンをクリックした場合に発生する価格の変更を反映するように直ちに更新されます。 ただし、GridView でビューステートを無効にしていない場合は、この変更を行った後にデータを GridView に手動で再バインドする必要があります。 これを実現するには、 メソッドを呼び出した直後に GridView の DataBind() メソッドを UpdateProduct 呼び出します。

図 20 は、おばあちゃんケリーのホームステッドが提供する製品を表示するときのページを示しています。 図 21 は、[Price +10%]\(価格 +10%\) ボタンが[おばあちゃんのボーイセンベリースプレッド]で 2 回クリックされた後の結果を示しています。[Price -10%]\(価格 -10%\) ボタンはノースウッド クランベリー ソース用に 1 回クリックされています。

GridView には、価格 +10% と価格 -10% ボタンが含まれています

図 20: GridView には、価格 +10% ボタンと価格 -10% ボタンが含まれています (フルサイズの画像を表示するにはクリックします)

1 番目と 3 番目の製品の価格は、価格 +10% ボタンと価格 -10% ボタンを使用して更新されました

図 21: 1 番目と 3 番目の製品の価格は、価格 +10% ボタンと価格 -10% ボタンを使用して更新されました (フルサイズの画像を表示するにはクリックします)

注意

GridView (および DetailsView) には、Buttons、LinkButtons、または ImageButtons を TemplateFields に追加することもできます。 BoundField と同様に、これらのボタンをクリックするとポストバックが発生し、GridView イベント RowCommand が発生します。 ただし、TemplateField にボタンを追加する場合、Buttons CommandArgument は ButtonFields を使用する場合と同様に行のインデックスに自動的に設定されません。 イベント ハンドラー内で RowCommand クリックされたボタンの行インデックスを決定する必要がある場合は、次のようなコードを使用して、TemplateField 内の宣言構文で Button の CommandArgument プロパティを手動で設定する必要があります。
<asp:Button runat="server" ... CommandArgument='<%# CType(Container, GridViewRow).RowIndex %>' />.

まとめ

GridView、DetailsView、および FormView の各コントロールには、Buttons、LinkButtons、ImageButtons を含めることができます。 このようなボタンをクリックすると、ポストバックが発生し、FormView コントロールと DetailsView コントロールでイベントが発生し、GridView のイベントがRowCommand発生ItemCommandします。 これらのデータ Web コントロールには、レコードの削除や編集など、コマンド関連の一般的なアクションを処理する機能が組み込まれています。 ただし、ボタンを使用することもできます。ボタンをクリックすると、独自のカスタム コードを実行して応答できます。

これを実現するには、 または RowCommand イベントのイベント ハンドラーを作成するItemCommand必要があります。 このイベント ハンドラーでは、最初に受信CommandName値をチェックして、クリックされたボタンを特定してから、適切なカスタム アクションを実行します。 このチュートリアルでは、ボタンと ButtonFields を使用して、指定したサプライヤーのすべての製品を中止するか、特定の製品の価格を 10% 増減させる方法について説明しました。

幸せなプログラミング!

著者について

7 冊の ASP/ASP.NET 書籍の著者であり、 4GuysFromRolla.com の創設者である Scott Mitchell は、1998 年から Microsoft Web テクノロジと協力しています。 Scott は独立したコンサルタント、トレーナー、ライターとして働いています。 彼の最新の本は サムズ・ティーチ・自分自身 ASP.NET 24時間で2.0です。 にアクセスmitchell@4GuysFromRolla.comすることも、ブログを介して アクセスすることもできます。これは でhttp://ScottOnWriting.NET確認できます。