Desenvolvimento - C#

Sort no GridView sem ir ao banco de dados novamente

Veja neste artigo como ordenar suas colunas com apenas um clique, sem precisar ir ao banco de dados novamente.

por Mauricio Junior



          Para quem desenvolve software utilizando a plataforma da Microsoft, usa muito o componente GridView. Esse componente serve para listar todos dados vindos de um banco de dados qualquer, pode ser SQL Server, MySQL, Oracle, Sybase e outros.

          Este componente é muito poderoso e te ajuda a listar os dados de forma simples e dinâmica. Existe um evento dentro desse objeto chamado Sort que serve para ordenar a coluna toda por ordem alfabética crescente ou decrescente.

          Hoje para preencher um GridView, é necessário atribuir as colunas, ter dados do XML ou  banco de dados ou tabelas em Excel ou qualquer outro meio de armazenamento de dados. No final, é necessário ter um DataSet ou DataTable preenchido para passar ao objeto GriView.

          O meu objetivo aqui não é mostrar passo a passo como preencher um gridview, o objetivo é ordenar os dados preenchidos do seu grid.

          O primeiro passo é colocar o seu grid na página .aspx.

<asp:GridView ID="grdContaCorrente" runat="server" Width="985px" PageSize="27" BackColor="White"

                    BorderColor="#EEEEEE" BorderStyle="Solid" BorderWidth="2px" CellPadding="3"

                    CellSpacing="1" GridLines="Horizontal" AllowPaging="True" AllowSorting="true"

                    AutoGenerateColumns="False"

                    onpageindexchanging="grdContaCorrente_PageIndexChanging"

                    onselectedindexchanged="grdContaCorrente_SelectedIndexChanged"

                    onrowcreated="grdContaCorrente_RowCreated"

                onsorting="grdContaCorrente_Sorting">

                    <FooterStyle BackColor="White" ForeColor="#000066" BorderStyle="Solid" />

                    <PagerStyle BackColor="White" ForeColor="#000066" HorizontalAlign="Left" BorderStyle="Solid" />

                    <SelectedRowStyle BackColor="#A0A4AC" Font-Bold="True" ForeColor="White" BorderStyle="Solid" />

                    <HeaderStyle BackColor="#D84040" Font-Bold="True" ForeColor="White" BorderStyle="Solid" />

                    <AlternatingRowStyle BackColor="#EEEEEE" BorderStyle="Solid" />   

       

                    <Columns>

                        <asp:CommandField SelectText="»»" ShowCancelButton="False" ShowSelectButton="True">

                            <ItemStyle BorderStyle="Solid" BorderWidth="2px" HorizontalAlign="Center" VerticalAlign="Middle" Width="1px" />

                        </asp:CommandField>

                        <asp:BoundField SortExpression="Agencia" DataField="Agencia" HeaderText="Agência" HtmlEncode="False" FooterText="">

                            <ItemStyle BorderStyle="Solid" BorderWidth="2px" HorizontalAlign="Center" VerticalAlign="Middle"/>

                        </asp:BoundField>

                        <asp:BoundField SortExpression="Conta" DataField="Conta" HeaderText="Conta" HtmlEncode="False" FooterText="">

                            <ItemStyle BorderStyle="Solid" BorderWidth="2px" HorizontalAlign="Center" VerticalAlign="Middle"/>

                        </asp:BoundField>

                        <asp:BoundField SortExpression="Nome" DataField="Nome" HeaderText="Nome" HtmlEncode="False" FooterText="">

                            <ItemStyle BorderStyle="Solid" BorderWidth="2px" HorizontalAlign="Left" VerticalAlign="Middle" />

                        </asp:BoundField>

                        <asp:BoundField SortExpression="CPFCNPJ" DataField="CPFCNPJ" HeaderText="CPF/CNPJ" HtmlEncode="False" FooterText="">

                            <ItemStyle BorderStyle="Solid" BorderWidth="2px" HorizontalAlign="Center" VerticalAlign="Middle" />

                        </asp:BoundField>

                        <asp:BoundField SortExpression="ContaConjunta" DataField="ContaConjunta" HeaderText="C. Conjunta" HtmlEncode="False" FooterText="">

                            <ItemStyle BorderStyle="Solid" BorderWidth="2px" HorizontalAlign="Center" VerticalAlign="Middle" />

                        </asp:BoundField>

                        <asp:BoundField SortExpression="DataCadastro" DataField="DataCadastro" HeaderText="Data Cadastro" HtmlEncode="False" FooterText="">

                            <ItemStyle BorderStyle="Solid" BorderWidth="2px" HorizontalAlign="Center" VerticalAlign="Middle" />

                        </asp:BoundField>

                        <asp:BoundField SortExpression="Situacao" DataField="Situacao" HeaderText="Situação" HtmlEncode="False" FooterText="">

                            <ItemStyle BorderStyle="Solid" BorderWidth="2px" HorizontalAlign="Center" VerticalAlign="Middle" />

                        </asp:BoundField>

                        <asp:BoundField SortExpression="SituacaoConciliacao" DataField="SituacaoConciliacao" HeaderText="Sit. Conciliação" HtmlEncode="False" FooterText="">

                            <ItemStyle BorderStyle="Solid" BorderWidth="2px" HorizontalAlign="Center" VerticalAlign="Middle" />

                        </asp:BoundField>

                        <asp:BoundField DataField="ContaCorrenteId" HeaderText="ContaCorrenteId" />

                    </Columns>

                    <HeaderStyle Font-Size="Smaller" />

                    <PagerStyle Font-Size="Smaller" />

                    <RowStyle Font-Size="Smaller" />

                    <PagerSettings Position="Bottom" Mode="NextPreviousFirstLast"

                        PreviousPageText="<img src='imagens/seta-esquerda.png' border='0' title='Página Anterior'/>"

                        NextPageText="<img src='imagens/seta-direita.png' border='0' title='Próxima Página'/>"

                        FirstPageText="<img src='imagens/seta-esquerda-ultima.png' border='0' title='Primeira Página'/>"

                        LastPageText="<img src='imagens/seta-direita-ultima.png' border='0' title='Última Página'/>" PageButtonCount="27" />

            </asp:GridView>

          Note que o meu grid possui muitos campos como: Agência, Conta, Nome, CPFCNPJ, ContaConjunta, DataCadastro e Situacao.

          O segundo passo foi colocar no gridview uma tag chamada AllowSorting=”true”, permite que as colunas sejam ordenadas. Isso não é tudo, é necessário seguir outros passos importantes que vem a seguir.

          O terceiro passo foi colocar em cada coluna uma tag chamada SortExpression=”NOME_DA_COLUNA”. O mesmo nome da coluna existente em seu objeto de dados.

          Além desses passos, preciso gerar um evento do próprio GridView. Esse evento chama OnSorting. Escolha na parte de Design e clique no botão Events localizado nas propriedades (properties). Imagem 1.

Imagem 1

          Note que a imagem está selecionada no evento Sorting. Basta clicar duas vezes em cima que, automaticamente um método é criado. (Code 2)

protected void grdContaCorrente_Sorting(object sender, GridViewSortEventArgs e)

{}

Code 2

          Para pegar o nome da coluna selecionada pelo usuário, basta utilizar o código seguinte. (Code 3)

String _coluna = e.SortExpression;

          Depois de ter o nome da coluna fica mais fácil fazer a ordenação. Na verdade é a principal etapa para ordenação, você precisa saber qual a coluna que o usuário clicou para ordenar.

          O quarto passo é ordenar os valores e preencher novamente o GridView. Muitos desenvolvedores escrevem o código indo novamente ao banco de dados. Não é errado fazer isso, porém, para evitar ir ao banco de dados a todo o momento e consumir muito tráfego na rede; é melhor ordenar o objeto de dados em vez de ir ao banco.

          Você pode armazenar no ViewState ou em Sessão todo o objeto de dados que no meu caso é um DataTable. Lembre-se que se o ViewState for muito grande, pode dar o erro sem memória. Para evitar isso, resolvi armazenar o meu DataTable em uma Sessão temporária. Code 4.

Session.Add("TEMP_SESSAO", _dtTable);

Code 4

          Para pegar essa Sessão novamente basta fazer da seguinte forma. Code 5.

DataTable _dtTable = (DataTable)Session["TEMP_SESSAO"];

Code 5

          Estou utilizando apenas um cast para transformar a sessão em DataTable novamente. Existem dois artigos escritos anteriormente que mostram como ordenar os dados no objeto. Segue o link dos dois:

1- http://ecode10.com/artigo/1073/Ordenando+no+DataTable.aspx

2- http://www.ecode10.com/artigo/924/Metodo+para+ordenar+DataTable.aspx

Nos dois links acima eu mostro como ordenar um objeto.  Code 6.

String _coluna = e.SortExpression;

_dtTable.DefaultView.Sort = _coluna;

this.grdContaCorrente.DataSource = _dtTable;

this.grdContaCorrente.DataBind();

Code 6

          O problema maior agora é fazer com que a ordem seja crescente ou decrescente. Pra isso é necessário armazenar a coluna anterior clicada, se a coluna for igual a última selecionada, basta acrescentar o desc. Criei um campo hidden na tela para armazenamento e depois fiz a verificação com a condição if. Veja o Code 7.

protected void grdContaCorrente_Sorting(object sender, GridViewSortEventArgs e)

    {

        try

        {

            DataTable _dtTable = (DataTable)Session["TEMP_SESSAO"];

            String _coluna = e.SortExpression;

            if (_coluna.Equals(hdColuna.Value))

                _coluna = _coluna + " desc";

            hdColuna.Value = _coluna;

            _dtTable.DefaultView.Sort = _coluna;

            this.grdContaCorrente.DataSource = _dtTable;

            this.grdContaCorrente.DataBind();

        }

        catch (Exception ex)

        {

            throw ex;

        }

    }

Code 7

          Depois de pegar a sessão, pego a coluna e armazeno na variável “_coluna”. Verifico com o if(_coluna.Equals(hdColuna.Value)) se o valor é o mesmo selecionado anteriormente. Se for igual, eu coloco o “ desc” e adiciono no campo hidden. O comando DefaultView.Sort = _coluna significa que os dados estão sendo ordenados pela coluna passada e depois o DataSource do grid recebe o objeto DataTable re-ordenado.

          Dessa maneira não vou ao banco de dados e ordeno todo o meu objeto com um clique.

Espero que tenha gostado e qualquer dúvida pode entrar em contato.

Mauricio Junior

Mauricio Junior - Formado pela Faculdade Anhanguera, Especialista pela FGV (Fundação Getúlio Vargas), Pós-Graduação em Docência Superior e cursando Mestrado na UNB Engenharia Elétrica; . Tenho 29 anos e possuo sete livros publicados pela editora Ciência Moderna e sou editor do Linha de Código.
Sou Certificado Microsoft MCP, MCAD e MVP, faço parte da comunidade ASPNETI.COM, onde publico artigos, vídeos, ebooks e livros Publico artigos, vídeos e podcast em outras comunidades. Trabalho como Analista de Sistemas / Desenvolvedor na empresa ATP S/A.
Blog:
blog.mauriciojunior.org
Site pessoal: www.mauriciojunior.org