0

完全に入力されている次のグリッドビューを定義しています。

    <asp:GridView runat="server" ID="chargeDetail" AutoGenerateColumns="false" DataKeyNames="LineItemNumber,DetailId,IsParking" CellSpacing="0" CellPadding="6"
     HorizontalAlign="Center" EnableViewState="true" ShowFooter="true">
        <Columns>
            <asp:BoundField DataField="StudentID" HeaderText="Student ID" ReadOnly="True" ItemStyle-HorizontalAlign="Center" />
            <asp:BoundField DataField="StudentName" HeaderText="Name" ReadOnly="true" />
            <asp:BoundField DataField="CampusName" HeaderText="Campus" ReadOnly="true" />
            <asp:TemplateField HeaderText="Description" ItemStyle-HorizontalAlign="Center">
                <ItemTemplate>
                    <asp:Label runat="server" ID="LineItemDetailLabel" Text='<%# IIf(Eval("Mandatory") = "1", Eval("LineItemDetail") + " *", Eval("LineItemDetail")) %>' />
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Item Cost" ItemStyle-HorizontalAlign="Center">
                <ItemTemplate>
                    $<asp:Label runat="server" ID="LineItemCostLabel" Text='<%# Eval("LineItemCost") %>' />
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Options" ItemStyle-HorizontalAlign="Center">
                <ItemTemplate>
                    <asp:Label runat="server" ID="lblOptionsAvailable" 
                     Text='<%# IIf(Eval("AttributesAvailable") = "1", "Options will be available to select on the next screen.", "No options available.") %>' />
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Pay Now" ItemStyle-HorizontalAlign="Center" FooterText="Total:">
                <ItemTemplate>
                    <asp:Checkbox runat="server" ID="cbLineItemSelected" Checked='<%# IIf(Eval("Selected") = "1", "True", "False") %>'
                     Enabled='<%# IIf(Eval("Mandatory") = "1", "False", "True") %>' AutoPostBack="True" OnCheckedChanged="cbLineItemSelected_CheckedChanged" />
                </ItemTemplate>
                <FooterStyle Font-Bold="True" HorizontalAlign="Right" />
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Total">
                <ItemTemplate>
                    $<asp:Label runat="server" ID="lblLineTotalCost" Text='<%# IIf(Eval("Selected") = "1", Eval("LineItemCost"), "0.00") %>' />
                </ItemTemplate>
                <FooterTemplate>
                    $<asp:Label runat="server" ID="lblTotal" />
                </FooterTemplate>
                <FooterStyle Font-Bold="True" />
            </asp:TemplateField>
        </Columns>
    </asp:GridView>

HeaderText="Options" の TemplateField では、可変数のドロップダウン リストを作成できる必要があります。学校が請求する可能性のある料金ごとに、任意の数の属性を関連付けることができます。たとえば、T シャツの料金ではサイズと色を収集する必要があり、各属性には複数のオプションがある場合があります。

現在、ラベルが正しく入力されていることがわかりますが、2 つのドロップダウン リスト (この場合は [サイズ] と [色]) を作成できるようにする必要があります。この手数料は彼らの請求に含まれます。Pay Now 列のチェックボックスに OnCheckedChanged イベントがあり、現在、合計列とフッター行の全体合計を更新していることがわかります。

親が選択できるように、イベントがチェックされたときにドロップダウンに入力することが理想的です。また、選択内容を正しく記録できるように、これらのドロップダウンからポスト バックを処理する方法も知っておく必要があります。

私が見つけたものから、ドロップダウンリストを配置できるネストされたグリッドビューを作成する必要があると推測していますが、それを機能させる方法の正しい方向を示す例が見つかりません。コードビハインドからドロップダウンに簡単に入力でき、正しい方向を指していれば、親が入力したデータにアクセスできます。少しの方向性またはより簡単な方法が必要です。

前もって感謝します!

4

1 に答える 1

0

OK、うまくいくと思われる解決策を思いつきました。グリッドビュー定義内で、次のようにドロップダウン リストを含む別のグリッドビューをネストしました。

        <asp:TemplateField HeaderText="Options" ItemStyle-HorizontalAlign="Center">
            <ItemTemplate>
                <asp:GridView runat="server" ID="gvOptions" AutoGenerateColumns="False" DataKeyNames="AttributeId" HorizontalAlign="center" EnableViewState="true"
                    GridLines="None" EmptyDataText="No available options." ShowHeader="False">
                    <Columns>
                        <asp:BoundField DataField="Description" ReadOnly="true" ItemStyle-HorizontalAlign="Center" />
                        <asp:TemplateField>
                            <ItemTemplate>
                                <asp:DropDownList runat="server" ID="ddlOptionSelection" DataTextField="Description" DataValueField="OptionId"
                                    EnableViewState="true" AutoPostBack="true" OnSelectedIndexChanged="ddlOptionSelection_SelectedIndexChanged">
                                </asp:DropDownList>
                            </ItemTemplate>
                        </asp:TemplateField>
                    </Columns>
                </asp:GridView>
            </ItemTemplate>
        </asp:TemplateField>

課題は、ネストされたグリッドビューのデータが親グリッドビューのデータ キーに依存していたため、すべてを結び付ける方法を見つけることでした。親の RowDataBound イベントは子 gridview を検出し、次のようにドロップダウンを設定します (gvOptions は子で、chargeDetail は親です)。

Protected Sub chargeDetail_RowDataBound(sender As Object, e As System.Web.UI.WebControls.GridViewRowEventArgs) Handles chargeDetail.RowDataBound
    If e.Row.RowType = DataControlRowType.DataRow Then
        Dim gv As GridView = DirectCast(e.Row.FindControl("gvOptions"), GridView)
        Dim cb As CheckBox = DirectCast(e.Row.FindControl("cbLineItemSelected"), CheckBox)
        Dim lineItem As String = chargeDetail.DataKeys(e.Row.RowIndex).Values("LineItemNumber")
        gv.DataSource = GetOptions(chargeDetail.DataKeys(e.Row.RowIndex).Values("DetailId"))
        gv.DataBind()

        Dim gridLineCount As Integer = gv.Rows.Count()
        Dim gridWorkingRow As Integer

        For gridWorkingRow = 0 To gridLineCount - 1
            Dim ddl As DropDownList = gv.Rows(gridWorkingRow).FindControl("ddlOptionSelection")
            Dim AttribId As Integer = gv.DataKeys(gridWorkingRow).Values("AttributeId")
            ddl.DataSource = PopulateOptions(AttribId)
            ddl.DataBind()
            ddl.SelectedValue = GetSelectedValue(AttribId, lineItem)

            If cb.Checked Then
                ddl.Enabled = True
            Else
                ddl.Enabled = False
            End If
        Next gridWorkingRow
    End If
End Sub

ドロップダウンの 1 つが変更されると、以下が発生します。データがデータベースに保存される方法に基づいて、属性とオプションのペアが連結されて単一のフィールドに保存されるため、すべてのオプションを再送信する方が簡単であることがわかりました。

Protected Sub ddlOptionSelection_SelectedIndexChanged(ByVal sender As Object, ByVal e As EventArgs)
    Dim ddlSender As DropDownList = DirectCast(sender, DropDownList)
    Dim row As GridViewRow = DirectCast(ddlSender.NamingContainer, GridViewRow)
    Dim gvOption As GridView = DirectCast(row.NamingContainer, GridView)
    Dim chargeDetailRow As GridViewRow = DirectCast(gvOption.Parent.Parent, GridViewRow)
    Dim LineItemNumber As Integer = CInt(chargeDetail.DataKeys(chargeDetailRow.RowIndex).Values("LineItemNumber"))

    Dim gridLineCount As Integer = gvOption.Rows.Count()
    Dim gridWorkingRow As Integer
    Dim OptionString As String = ""

    For gridWorkingRow = 0 To gridLineCount - 1
        Dim ddl As DropDownList = gvOption.Rows(gridWorkingRow).FindControl("ddlOptionSelection")
        Dim AttribId As String = gvOption.DataKeys(gridWorkingRow).Values("AttributeId")

        If gridWorkingRow = gridLineCount - 1 Then
            OptionString = OptionString + AttribId + ":" + ddl.SelectedValue
        Else
            OptionString = OptionString + AttribId + ":" + ddl.SelectedValue + ","
        End If
    Next gridWorkingRow

    Dim PortalConn As New SqlConnection
    PortalConn.ConnectionString = ConfigurationManager.ConnectionStrings("PortalConnStr").ConnectionString
    PortalConn.Open()

    Dim WriteBackSQL As New SqlCommand("sp_schedulePickup_UpdateOption", PortalConn)
    WriteBackSQL.CommandType = Data.CommandType.StoredProcedure
    WriteBackSQL.Parameters.Add(New SqlParameter("@SessionID", Session.SessionID.ToString()))
    WriteBackSQL.Parameters.Add(New SqlParameter("@LineItemNumber", LineItemNumber))
    WriteBackSQL.Parameters.Add(New SqlParameter("@Option", OptionString))

    Dim returnStatus As Integer
    Dim rsReturn As SqlDataReader = WriteBackSQL.ExecuteReader()
    Do While rsReturn.Read()
        returnStatus = rsReturn("ReturnStatus")
    Loop
    rsReturn.Close()
    rsReturn = Nothing

    PortalConn.Close()
    PortalConn = Nothing

    chargeDetail.DataSource = GetChargeDetails()
    chargeDetail.DataBind()
    getTotal()
End Sub
于 2012-06-12T16:20:48.670 に答える