Accessing Repeater Item Controls in OnChange JavaScript

拥有回忆 提交于 2019-12-13 04:37:31

问题


I've got a repeater control containing a textbox and a label. I want to set the label value based on the value the user sets in the textbox, on the client-side to avoid a round-trip to the server.

I wrote a JavaScript function which is called by the textbox OnChange event. Now I just need to access the textbox and label in that function. I understand I should be accessing the controls via <%# Container.FindControl(...).ClientID %> but I cannot get it to work in the OnChange event. I also tried <%# Container.ItemIndex %>, in case there was a problem with the nested quotes, but that didn't work either.

I'm a novice with ASP.NET so I assume I'm missing something obvious.

Here's what I've got so far (currently attempting to use <%# Container.ItemIndex %>):

<asp:Content ID="Content3" ContentPlaceHolderID="regionBody" runat="server">
    <table class="DataGrid">
        <tr class="HeaderStyle">
            <td>Item</td>
            <td>Weight (kg)</td>
            <td>Total Volume (m3):</td>
        </tr>
        <asp:Repeater ID="rptItems" runat="server" 
            OnItemDataBound="rptItems_ItemDataBound" >
            <ItemTemplate>
                <tr class='<%# Container.ItemIndex % 2 == 0 
                            ? "ItemStyle" 
                            : "AlternatingItemStyle"  %>' 
                    style="text-align: center">
                    <td>
                        <asp:Label ID="lblItemNum" runat="server" />
                    </td>
                    <td>
                        <asp:TextBox ID="txtWeight" Height="20px" Width="40px" 
                            runat="server" Visible="true" 
                            OnChange="ValidateItemWeightAndSetVolume(0);" />
                    </td>
                    <td>
                        <asp:Label ID="lblVolume" runat="server" 
                            Visible="true" CssClass="numericLeft" />
                    </td>
                </tr>
            </ItemTemplate>
        </asp:Repeater>
    </table>
</asp:Content>

And here's the JavaScript function:

function ValidateItemWeightAndSetVolume(itemIndex) { 
    var weightId = "regionBody_rptItems_txtWeight_" + itemIndex;
    var volumeId = "regionBody_rptItems_lblVolume_" + itemIndex;
    var txtWeight = document.getElementById(weightId);
    var lblVolume = document.getElementById(volumeId);

    var volume = 0;
    var validated = ValidateItemWeight(txtWeight);
    if (validated) {
        var weight = parseFloat(txtWeight.value);
        volume = weight / <%=VOLUMETRIC_WEIGHT_CONVERSION%>;
    }

    // asp:label is rendered as a span in HTML.  So to set the value, 
    //  have to set the inner HTML.
    lblVolume.innerHTML = volume;
}

The second function, ValidateItemWeight, just checks the user entered a numeric value between certain limits and displays an alert if they didn't.

The code above works since I'm just passing an integer into the function: OnChange="ValidateItemWeightAndSetVolume(0);", but that is only applicable to the first repeater item. If I modify it as follows the function doesn't run: OnChange="ValidateItemWeightAndSetVolume(<%# Container.ItemIndex %>);"


回答1:


You can use <%# Container.ItemIndex %> as ourmandave suggested in the comment:

... OnChange="ValidateItemWeightAndSetVolume(<%# Container.ItemIndex %>`);" />

But it would be better if you could use javascript to get the label (instead of index concat with string-id) like this (jQuery):

Use OnChange = ValidateItemWeightAndSetVolume(this) and change the js function like this:

function ValidateItemWeightAndSetVolume(textBox) {    
    var txtWeight = textBox;
    var lblVolume = $(textBox).closest("td").next("td").find("span")[0];
    var volume = 0;
    var validated = ValidateItemWeight(txtWeight);
    if (validated) {
        var weight = parseFloat(txtWeight.value);
        volume = weight / <%=VOLUMETRIC_WEIGHT_CONVERSION%>;
    }

    lblVolume.innerHTML = volume;
}

Also, you can use a HeaderTemplate and FooterTemplate inside a Repeater like this:

<asp:Repeater ID="rptItems" runat="server">
    <HeaderTemplate>
        <table class="DataGrid">
            <tr class="HeaderStyle">
                <td>Item</td>
                <td>Weight (kg)</td>
                <td>Total Volume (m3):</td>
            </tr>
    </HeaderTemplate>
    <ItemTemplate>
        <!-- Your item template here -->
    </ItemTemplate>
    <FooterTemplate>
        </table>
    </FooterTemplate>
</asp:Repeater>

This keeps the mark-up clean imo.



来源:https://stackoverflow.com/questions/33905959/accessing-repeater-item-controls-in-onchange-javascript

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!