C# - CRUD com TreeView e DataGridView
Vamos realizar as operações básicas de acesso e manutenção de dados via ADO .NET em um banco de dados SQL Server usando os controles TreeView e DataGridView. |
Na verdade os controles serão usados apenas para exibirmos as informações da tabela Alunos do banco de dados Cadastro.mdf.
Vamos exibir os nomes dos alunos no controle TreeView e os detalhes no controle DataGridView de forma que ao selecionar um nome no controle TreeView as informações serão exibidas em controles TextBox no formulário e estarão prontas para serem atualizadas ou excluídas.
É um projeto simples que mostra de forma básica como acessar e realizar as operações CRUD em uma aplicação C#.
Definindo o banco de dados e a tabela
O banco de dados Cadastro.mdf e a tabela Alunos podem ser criados diretamente no SQL Server Management Studio com a seguinte estrutura :
A tabela Alunos possui os seguintes campos:
|
ou usando o script a seguir:
1- Script para o banco de dados Cadastro.mdf ser criado na pasta c:\dados
USE [master] GO CREATE DATABASE [Cadastro] ON PRIMARY ( NAME = N'Cadastro', FILENAME = N'c:\dados\Cadastro.mdf' , SIZE = 3072KB , MAXSIZE = UNLIMITED, FILEGROWTH = 1024KB ) LOG ON ( NAME = N'Cadastro_log', FILENAME = N'c:\dados\Cadastro_log.ldf' , SIZE = 1024KB , MAXSIZE = 2048GB , FILEGROWTH = 10%) GO |
Se você for usar script acima atente para o fato que o local de criação do banco de dados será na pasta c:\dados . Portanto você deve alterar a pasta para o seu local preferido.
2- Script para criar a tabela Alunos
USE [Cadastro] GO SET ANSI_NULLS ON GO SET QUOTED_IDENTIFIER ON GO CREATE TABLE [dbo].[Alunos]( [id] [int] IDENTITY(1,1) NOT NULL, [nome] [nvarchar](50) NULL, [email] [nvarchar](150) NULL, [idade] [int] NULL, [endereco] [nvarchar](150) NULL, [ativo] [bit] NULL, CONSTRAINT [PK_Alunos] PRIMARY KEY CLUSTERED ( [id] ASC )WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY] ) ON [PRIMARY] |
Criando o projeto no Visual C# 2010 Express Edition
Abra o Visual C# 2010 Express Edition e crie um novo projeto no menu File-> New Project escolhendo o template Windows Forms Application com o nome UsandoTreeView e clique no botão OK;
A seguir no formulário form1.cs inclua os controles : TreeView (tvwAlunos) , DataGridView(gdvDetalhes), 5 TextBox , 1 CheckBox(chkAtivo) e 4 Buttons conforme o leiaute da figura abaixo:
Controles do formulário form1.cs: - TextBox :
- Button :
|
Agora vamos definir uma string de conexão no arquivo App.Config. Para criar o arquivo de configuração no menu Project clique em Add New Item e a seguir selecione o template Application Configuration FIle e aceite o nome padrão clicando em Add;
A seguir defina a string de conexão conforme mostra a figura abaixo onde iremos acessar o banco de dados Cadastro.mdf do SQL Server;
Para podermos acessar o arquivo de configuração e obter a string de conexão definida temos que incluir uma referência a System.Configuration via menu Project clicando em Add Reference e na tab .NET selecionar o item desejado e clicar em OK;
Temos também de definir no formulário form1.cs seguintes namespaces:
using
System;using
System.Data;using
System.Windows.Forms;using
System.Data.SqlClient;using
System.Configuration;Definindo o código
Agora vamos definir o código da aplicação e antes de prosseguir quero deixar claro que:
Definindo as variáveis usadas no projeto no início do formulário:
static bool incluir = false; static string strConexaoSQL = ConfigurationManager.ConnectionStrings["conexaoSQL_Cadastro"].ToString(); SqlDataReader dr; SqlConnection conn = new SqlConnection(strConexaoSQL); |
Definindo a rotina carregaDadosTreeView para carregar o controle TreeView para exibir o nome dos alunos da tabela Alunos:
/// <summary> /// Carrega dados no TreeView /// </summary> private void carregaDadosTreeView() { tvwAlunos.Nodes.Clear(); try { conn.Open(); SqlCommand cmd = new SqlCommand("SELECT nome FROM alunos", conn); dr = cmd.ExecuteReader(); while (dr.Read()) { tvwAlunos.Nodes.Add(dr.GetValue(0).ToString()); } dr.Close(); } catch (Exception ex) { MessageBox.Show(ex.ToString()); } finally { conn.Close(); } } |
Rotina carregaDadosGridView para carregar os dados da tabela Alunos no controle DataGridView
/// <summary> /// Carrega dados no GridView /// </summary> private void carregaDadosGridView() { try { conn.Open(); SqlCommand cmd = new SqlCommand("SELECT * FROM Alunos", conn); DataSet ds = new DataSet(); SqlDataAdapter da = new SqlDataAdapter(cmd); da.Fill(ds); gdvDetalhes.DataSource = ds.Tables[0]; dr.Close(); } catch (Exception ex) { MessageBox.Show(ex.ToString()); } finally { conn.Close(); } } |
Rotina Vincula() que chama as duas rotinas acima:
/// <summary> /// Vincula os dados no TreeView e GridView /// </summary> private void vincula() { carregaDadosTreeView(); carregaDadosGridView(); }
|
Código do evento Load do formulário que chama a rotina vincula():
/// <summary> /// Chama a rotina para vincular os dados no /// TreeView e DataGridView /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void Form1_Load(object sender, EventArgs e) { vincula(); } |
A rotina carregaDados() usada para exibir os dados do aluno selecionado no controle TreeView nos controles TextBox:
/// <summary> /// Carrega os dados a partir da tabela Alunos pelo nome /// </summary> /// <param name="nome"></param> private void carregaDados(string nome) { try { conn.Open(); SqlCommand cmd = new SqlCommand("SELECT * FROM alunos where nome = '" + nome +"'" , conn); dr = cmd.ExecuteReader(); while (dr.Read()) { txtCodigo.Text = dr["id"].ToString(); txtNome.Text = dr["nome"].ToString(); txtEndereco.Text = dr["endereco"].ToString(); txtEmail.Text = dr["email"].ToString(); txtIdade.Text = dr["idade"].ToString(); chkAtivo.Checked = (Convert.ToBoolean(dr["ativo"]) == true ? true : false); } dr.Close(); } catch (Exception ex) { MessageBox.Show(ex.ToString()); } finally { conn.Close(); } } |
Código do evento AfterSelect do controle TreeView que chama a rotina carregaDados quando um nó do controle for selecionado;
Isso feito obtendo o nome do Nó selecionado usando o método SelectedNode e chamando a rotina para obter as informação pelo nome obtido:
string strNome = this.tvwAlunos.SelectedNode.Text.ToString();
A variável incluir é definida como false de forma que a inclusão não será
possível até que seu valor seja true;
/// <summary> /// Após selecionar um item no TreeView /// chama a rotina para preencher os textbox /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void tvwAlunos_AfterSelect(object sender, TreeViewEventArgs e) { incluir = false; string strNome = this.tvwAlunos.SelectedNode.Text.ToString(); carregaDados(strNome); } |
O código definido acima faz com que quando a aplicação for iniciada os controles TreeView e DataGridView seja preenchidos com os dados da tabela Alunos conforme mostra a figura abaixo:
Realizando a manutenção dos dados
Vamos agora definir o código para alterar, incluir e excluir dados da tabela Alunos. Faremos isso diretamente no formulário usando o evento Click de cada um dos botões de comando.
Utilizaremos instruções SQL no formato texto , o que não é muito aconselhável por permitir a injeção SQL. O mais indicado seria utilizar stored procedures , mas mostrarei isso em outro artigo.
As instruções SQL usadas são:
Estamos usando o método ExecuteNonQuery do objeto Command para executar as instruções SQL. Ele não retorna nenhum registro.
1- Código do evento Click do botão Limpar que chama a rotina limpaControles e põe o foco no controle txtNome:
private void btnLimpar_Click(object sender, EventArgs e) { limpaControles(); txtNome.Focus(); incluir = true; } |
Rotina limpaControles() usada para limpar os controles TextBox e CheckBox do formulário:
/// <summary> /// Limpa os controles TextBox e checkbox /// do container GroupBox /// </summary> private void limpaControles() { foreach (Control ctrl in grpAlunos.Controls) { if (ctrl is TextBox) { ((TextBox)ctrl).Clear(); } if (ctrl is CheckBox) { ((CheckBox)ctrl).Checked = false; } } } |
2- Código do evento Click do botão Novo que usa a instrução SQL INSERT INTO para incluir dados na tabela Alunos:
/// <summary> /// Incluir um novo registro na tabela Alunos /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void btnNovo_Click(object sender, EventArgs e) { if (incluir) { if ((txtNome.Text != string.Empty) && (txtEmail.Text != string.Empty) && (txtEndereco.Text != string.Empty)) { try { conn.Open(); int valor = chkAtivo.Checked == true ? 1 : 0; string sql = "Insert Into Alunos Values(" + "'" + txtNome.Text + "','" + txtEmail.Text + "'," + txtIdade.Text + ",'" + txtEndereco.Text + "'," + valor + ");"; SqlCommand cmd = new SqlCommand(sql, conn); cmd.ExecuteNonQuery(); MessageBox.Show("Registro incluído na tabela Alunos."); conn.Close(); vincula(); } catch (Exception ex) { MessageBox.Show(ex.ToString()); } finally { conn.Close(); incluir = false; } } else { MessageBox.Show("Valores inválidos."); } } else { incluir = false; MessageBox.Show("Limpe os controles e informe novos valores para incluir um registro."); } } |
3- Código do evento Click do botão Atualizar que usa a instrução SQL UPDATE SET para incluir dados na tabela Alunos:
/// <summary> /// Atualiza os dados da tabela Alunos pelo /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void btnAtualizar_Click(object sender, EventArgs e) { if ((txtCodigo.Text != string.Empty) && (txtNome.Text != string.Empty)) { try { conn.Open(); int valor = chkAtivo.Checked == true ? 1 : 0; string sql = "update Alunos set nome = '" + txtNome.Text + "', email = '" + txtEmail.Text + "', idade = " + txtIdade.Text + ", endereco = '" + txtEndereco.Text + "', ativo = " + valor + ";"; SqlCommand cmd = new SqlCommand(sql, conn); cmd.ExecuteNonQuery(); MessageBox.Show("Registros atualizados na tabela Alunos."); conn.Close(); vincula(); } catch (Exception ex) { MessageBox.Show(ex.ToString()); } finally { conn.Close(); } } else { MessageBox.Show("Preencha os dados do Aluno."); } } |
4- Código do evento Click do botão Deletar que usa a instrução SQL DELETE FROM para excluir dados na tabela Alunos:
/// <summary> /// Deleta os registros da tabela alunos pelo código do aluno /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void btnDeletar_Click(object sender, EventArgs e) { if (txtCodigo.Text != string.Empty) { try { conn.Open(); SqlCommand cmd = new SqlCommand("DELETE FROM Alunos WHERE id=" + Convert.ToInt32(txtCodigo.Text) + ";", conn); cmd.ExecuteNonQuery(); MessageBox.Show("Registro excluído com sucesso."); conn.Close(); vincula(); } catch (Exception ex) { MessageBox.Show(ex.ToString()); } finally { conn.Close(); } } else { MessageBox.Show("Informe o código do aluno."); } } |
Destaques do código:
Estamos usando a instrução try/Catch/Finally para realizar o tratamento de exceções nas rotinas. O bloco try-catch-finally é usado para envolver o código onde existe a possibilidade de uma exceção/erro ocorrer. Um bloco try-catch-finally é constituído das seguintes seções :
O operador ternário esta sendo usado para avaliar se o controle CheckBox esta ou não marcado.
int valor = chkAtivo.Checked == true ? 1 : 0;
o "?" funciona como um if :
No exemplo, como o campo da tabela para armazenar este valor é do tipo bit devemos gravar o valor zero (0) (false) ou um (1) (true).
Para concluir temos o código que usamos para validar a entrada de dados nos controles TextBox do formulário:
1- Aceita somente números e backspace para a idade : txtIdade
private void txtIdade_KeyPress(object sender, KeyPressEventArgs e) { if (!Char.IsDigit(e.KeyChar) && e.KeyChar != (char)8) e.Handled = true; } |
1- Aceita somente alfanuméricos e backspace para o email e o endereço : txtEmail e txtEndeco
private void txtNome_KeyPress(object sender, KeyPressEventArgs e) { if (Char.IsDigit(e.KeyChar) && e.KeyChar != (char)8) { e.Handled = true; } } private void txtEndereco_KeyPress(object sender, KeyPressEventArgs e) { if (Char.IsDigit(e.KeyChar) && e.KeyChar != (char)8) { e.Handled = true; } } |
Dessa forma temos uma aplicação simples que permite realizar operações CRUD em um banco de dados SQL Server. Todo o código foi mostrado e as orientações estão detalhadas para você reproduzir o projeto.
O projeto completo esta no Super DVD .NET e no Super CD .NET
"E, se alguém ouvir as minhas palavras,
e não crer, eu não o julgo: porque eu vim, não para julgar o mundo, mas para
salvar o mundo."
João 12:47
Referências: