Как реализовать полный выбор строки в GridView без кнопки выбора?

#c# #asp.net #gridview #selectedindexchanged

#c# #asp.net #просмотр сетки #selectedindexchanged #gridview

Вопрос:

Я реализую функцию, которая заключается в том, что когда пользователь нажимает на любую точку строки в GridView, строка будет выбрана вместо кнопки выбора.

введите описание изображения здесь

Чтобы реализовать это, я использую следующий код:

 protected void GridView1_RowDataBound(object sender, GridViewRowEventArgs e)
{
    if (e.Row.RowType == DataControlRowType.DataRow)
    {
        // Set the hand mouse cursor for the selected row.
        e.Row.Attributes.Add("OnMouseOver", "this.style.cursor = 'hand';");

        // The seelctButton exists for ensuring the selection functionality
        // and bind it with the appropriate event hanlder.
        LinkButton selectButton = new LinkButton()
        {
            CommandName = "Select",
            Text = e.Row.Cells[0].Text
        };

        e.Row.Cells[0].Controls.Add(selectButton);
        e.Row.Attributes["OnClick"] =
             Page.ClientScript.GetPostBackClientHyperlink(selectButton, "");
    }
}
  

С приведенным выше кодом возникают следующие проблемы:

  • Это работает нормально, только если для I EnableEventValidation для страницы установлено значение false .
  • SelectedIndexChanged Запускается только в том случае, если Grid.DataBind() вызывается Page_Load для страницы (при каждой обратной отправке).

Я делаю что-то не так? Есть ли лучшая реализация?


Редактировать: Когда EnableEventValidation установлено значение true , появится следующая ошибка:

Недопустимый аргумент обратной передачи или обратного вызова. Проверка события включена с помощью в конфигурации или <%@ Page EnableEventValidation=»true» %> на странице. В целях безопасности эта функция проверяет, что аргументы для событий обратной отправки или callback исходят от серверного элемента управления, который первоначально их отобразил. Если данные действительны и ожидаемы, используйте ClientScriptManager.Метод RegisterForEventValidation для регистрации данных обратной передачи или callback для проверки.

Ответ №1:

Вы должны добавлять это при каждой обратной передаче, а не только при привязке данных. Поэтому вам следует использовать RowCreated-событие GridView.

Например

(C #):

 protected void GridView1_RowCreated(object sender, System.Web.UI.WebControls.GridViewRowEventArgs e)
{
    if (e.Row.RowType == DataControlRowType.DataRow) {
        e.Row.Attributes["onmouseover"] = "this.style.cursor='pointer';this.style.textDecoration='underline';";
        e.Row.Attributes["onmouseout"] = "this.style.textDecoration='none';";
        e.Row.ToolTip = "Click to select row";
        e.Row.Attributes["onclick"] = this.Page.ClientScript.GetPostBackClientHyperlink(this.GridView1, "Select$"   e.Row.RowIndex);
    }
}
  

(VB.Net ):

 Private Sub GridView1_RowCreated(ByVal sender As Object, ByVal e As System.Web.UI.WebControls.GridViewRowEventArgs) Handles GridView1.RowCreated
    If e.Row.RowType = DataControlRowType.DataRow Then
        e.Row.Attributes("onmouseover") = "this.style.cursor='pointer';this.style.textDecoration='underline';"
        e.Row.Attributes("onmouseout") = "this.style.textDecoration='none';"
        e.Row.ToolTip = "Click to select row"
        e.Row.Attributes("onclick") = Me.Page.ClientScript.GetPostBackClientHyperlink(Me.GridView1, "Select$" amp; e.Row.RowIndex)
    End If
End Sub
  

Комментарии:

1. это не решает проблему установки EnableEventValidation значения false.

2. @Homam: вы использовали мой код и все еще получаете ошибку «недопустимый аргумент обратной отправки / callback»? Я не могу воспроизвести эту ошибку в своем проекте, но для этого может быть другая причина. Сейчас у меня нет времени для дальнейшего изучения этого. Вы могли бы использовать ClientScriptManager. RegisterForEventValidation , чтобы избежать этого. Может быть, эта ссылка поможет.

3. На каком языке описывается стиль? Я пробовал использовать CSS, но, похоже, это не работает. Например, это не background-color, а backgroundColor.

Ответ №2:

Вместо того, чтобы делать это на RowCreated , вы могли бы сделать это на Render() . Таким образом, вы могли бы использовать перегрузку GetPostBackClientHyperlink с помощью true on registerForEventValidation и избежать ошибки «недопустимый аргумент обратной передачи / callback».

Что-то вроде этого:

 protected override void Render(HtmlTextWriter writer)
    {
      foreach (GridViewRow r in GridView1.Rows)
      {
        if (r.RowType == DataControlRowType.DataRow)
        {
          r.Attributes["onmouseover"] = "this.style.cursor='pointer';this.style.textDecoration='underline';";
          r.Attributes["onmouseout"] = "this.style.textDecoration='none';";
          r.ToolTip = "Click to select row";
          r.Attributes["onclick"] = this.Page.ClientScript.GetPostBackClientHyperlink(this.GridView1, "Select$"   r.RowIndex,true);

        }
      }

      base.Render(writer);
    }
  

Комментарии:

1. Это также решило мою проблему. Все другие сообщения в Интернете говорят вам отключить EnableEventValidation , что открывает ваш сайт для инъекционных атак, это единственный правильный ответ.

Ответ №3:

 <style type="text/css">
    .hiddenColumn
    {
        display: none;
    }

    .rowGrid
    {
        cursor: pointer;
    }
</style>

<asp:GridView runat="server" ID="GridView1" AutoGenerateColumns="true" >
            <RowStyle CssClass="rowGrid" />
            <Columns>
                <asp:CommandField ButtonType="Button" ShowSelectButton="true" HeaderStyle-CssClass="hiddenColumn"
                    ItemStyle-CssClass="hiddenColumn" FooterStyle-CssClass="hiddenColumn" />
            </Columns>
        </asp:GridView>

<script type="text/javascript">
        $(function () {
            $("#<%= GridView1.ClientID %> tr.rowGrid")
            .live("click", function (event) {
                $(this).find("input[type='button'][value='Select']").click();
            });

            $("#<%= GridView1.ClientID %> input[type='button'][value='Select']")
                .live("click", function (event) {
                    event.stopPropagation();
                });

        });
    </script>
  

Ответ №4:

Попробуйте это, добавьте событие OnSelectedIndexChanged в grid

    OnSelectedIndexChanged="Grid_SelectedIndexChanged"
  

а затем в коде за

  protected void Grid_SelectedIndexChanged(object sender, EventArgs e)
{
    GridViewRow row = gvSummary.SelectedRow;
    //Int32 myvalue= Convert.ToInt32(row.Attributes["ColumnName"].ToString());
   } 
  

и установите EnableViewState=»false»
но здесь вам нужно выполнить еще две вещи, которые вы уже сделали в своем коде, означает
установите для EnableEventValidation значение false и привязку к сетке данных при загрузке страницы..

Ответ №5:

Попробуйте использовать <asp:LinkButton> вокруг вашего <tr> кода в ASPX, установите событие LinkButton CommandName='Select' И в item command, обработайте эту команду и задайте стиль выбранной строки!

Комментарии:

1. вы уверены, что наличие linikbutton между td и tr генерирует действительный, полностью совместимый HTML?

2. @Davide Piras: HTML, соответствующий стандартам, не был упомянут в вопросе в качестве требования! Если это требование, то не принимайте решение! Я показал некоторые возможности!

3. Я не согласен, я не голосовал против вас и не буду, но даже если вы не упоминались в оригинальном посте, давайте, мы летом 2011 (почти), давайте дадим только кроссбраузерные и полностью совместимые ответы 🙂 😉

4. @Давиде Пирас: Меня не беспокоят голоса «против»! Я полностью согласен с вами по поводу соответствия стандартам! Но я просто пытался помочь! Ни больше, ни меньше! Я столкнулся с подобной ситуацией, как @Homan, но тогда мне пришлось как можно скорее запустить это на рабочем сервере. Итак, тогда я не мог позволить себе искать соответствие стандартам! 😉 Подумал, что этот парень тоже был в похожей ситуации и мог бы извлечь выгоду из того, что я сделал в то время в качестве быстрого исправления. Приветствия! 🙂