Если обновления должны запускаться при изменении текста, вам следует использовать OnTextChanged
событие TextBox
и установить для AutoPostBack
значение true.
EDIT
Чтобы избежать дублирования усилий, используя вышеупомянутый подход, вы можете найти индекс строки, используя технику, которую Панкадж Гарг обрисовал в своем ответе:
int rowIndex = ((GridViewRow)((TextBox)sender).NamingContainer).RowIndex;
Самым большим предупреждением для этого подхода является то, что он не прощает изменений в разметке. Если бы вы обернули TextBox
в другой элемент управления, который реализует INamingContainer
, пример выше сломался бы. Например:
<asp:TemplateField>
<asp:Panel ID="Panel1" runat="server"> <!-- becomes the naming container -->
<asp:TextBox ID="TextBox1" runat="server" onchange='valueChanged(<%# Container.ItemIndex %>);' />
</asp:Panel>
</asp:TemplateField>
При этом вы хотели бы соответствующим образом отметить свою разметку, чтобы другие разработчики знали, что следует соблюдать осторожность при внесении изменений.
EDIT
В качестве альтернативы вы также можете запустить обратную передачу в JavaScript, используя onchange
событие TextBox
:
<script type="text/javascript">
valueChanged = function(rowIndex){
__doPostBack("<%= GridView1.ClientID %>", rowIndex);
}
</script>
<asp:GridView ID="GridView1" runat="server" DataKeyNames="ID" ...>
<Columns>
<asp:TemplateField>
<asp:TextBox ID="TextBox1" runat="server" onchange='valueChanged(<%# Container.ItemIndex %>);' />
</asp:TemplateField>
</Columns>
</asp:GridView>
В выделенном фрагменте кода переопределите метод RaisePostBackEvent
и поместите туда логику обновления:
protected override void RaisePostBackEvent(IPostBackEventHandler source, string eventArgument)
{
base.RaisePostBackEvent(source, eventArgument);
if (source == GridView1)
{
int rowIndex = int.Parse(eventArgument);
TextBox txt = GridView1.Rows[rowIndex].FindControl("TextBox1") as TextBox;
if (txt != null)
{
var id = (int)GridView1.DataKeys[rowIndex]["ID"];
var text = txt.Text.Trim();
//update the database
}
}
}