VB.NET - SQL Server e Entity Framework na Copa do mundo de 2014 - III


Na segunda parte do artigo eu apresentei os formulários para cadastro de grupos, seleções e jogadores. Vamos continuar agora com os formulários para cadastro das sedes, dos jogos das 1a fase e da atualização de resultados desses jogos permitindo a simulação da classificação.

Quero destacar neste artigo as consultas LINQ que usando os recursos de navegação do Entity Data Model permitem selecionar informações das entidades de uma forma simples e flexível.

A LINQ é baseada em um conjunto de operadores de consulta, definidos como métodos de extensão, que trabalham com qualquer objeto que implemente a interface IEnumerable<T>.

A sintaxe básica da linguagem é:

var <variável> = from <elemento da lista> in <lista de dados>
                      where <clausula>
                      select <elemento>
Dim <variável> = from <elemento da lista> in <lista de dados>
                       where <clausula>
                       select <elemento>
C# VB .NET

Exemplo usando a sintaxe VB .NET :

Dim dados = From produtos In db.Products
                 Where produtos.UnitPrice > 50
                 Order By produtos.ProductName
                 Select produtos.ProductName, produtos.UnitPrice

A consulta LINQ To SQL inicia com a cláusula From e em seguida o operador de condição Where depois ordenação com Order By, e, no final o operador de seleção Select.

Um dos motivos desta inversão de ordens é  o uso recurso IntelliSense, pois quando você indica primeiro a origem dos dados ele pode mostrar as listas de membros de tipos nos objetos em sua coleção. Outro motivo , segundo Anders Hejlsberg , seria que a ordem esta mais próxima da nossa lógica de pensamento. Quando você digita uma instrução SQL iniciando com Select na verdade você já esta pensando na origem dos dados , condições, agrupamentos. etc. (você concorda?)

A cláusula From é a mais importante do LINQ pois é usada em todas as consultas.

Uma consulta deve sempre começar com From. (O Select pode estar implícito o From não.)

Aplicando o esquema tático - Implementando a camada de interface e suas funcionalidades - II

Em cada formulário eu vou destacar somente o código mais relevante. Como as funcionalidades para incluir, alterar e excluir estão presentes em todos os formulário eu não vou repetir o código para cada um dos formulários, vou apresentar o código apenas uma vez.

1- Formulário de cadastro das Sedes

O formulário para gerenciar as sedes da copa do mundo não apresenta nenhuma novidade. Novamente estamos armazenando as imagens das sedes no banco de dados SQL Server como fizemos com as fotos dos jogadores.

Eu criei uma pasta chamada Estadios no projeto e nela inclui algumas fotos dos estádios das sedes apenas para exemplo.

Neste formulário temos os seguintes controles:

Abaixo vemos o leiaute do formulário onde o usuário poderá inserir, alterar e excluir os grupos definidos para as seleções do mundial de 2014.

2- Formulário de cadastro dos Jogos da 1a fase do Mundial

No formulário para cadastrar os jogos da copa do mundo o usuário deve informar o nome da seleção, a localização e nome da bandeira da seleção, que será armazenada em uma pasta na aplicação, e o grupo a que a seleção pertence. As bandeiras de cada seleção serão exibidas automaticamente.

Neste formulário temos os seguintes controles:

O leiaute do formulário é visto a seguir:

Este formulário é muito importante e todos os demais formulários para cadastrar os jogos das oitavas, quartas, semi e final se baseiam neste formulário.

Quando o formulário for carregado os controles ComboBox serão carregados com informações das horas, das sedes, grupos e das seleções, que foram previamente cadastrados, de forma que o usuário deverá apenas selecionar os valores nos controles combobox.

A carga dos controles é feita no evento Load do formulário conforme o código a seguir:

  Private Sub FormJogos_Load(sender As Object, e As EventArgs) Handles MyBase.Load
        carregaGrupos()
        carregaSedes()
        carregaSelecoes()
        cboHora.SelectedIndex = 0
        carregaGrid()
    End Sub

A combobox cboHora é carregada manualmente usando sua propriedade items onde digitamos os valores para o horário dos jogos conforme abaixo:

A seguir temos o código de cada um demais métodos:

1- carregaGrupos

Carrega a combobox cboGrupo com informações da entidade Grupos usando uma consulta LINQ :

 Private Sub carregaGrupos()
        Try
            Using ctx As New Copa2014Entities
                Dim consulta = From grupo In ctx.Grupos
                                      Where grupo.GrupoId < 9
                                      Select grupo
                cboGrupo.DisplayMember = "Nome"
                cboGrupo.ValueMember = "GrupoId"
                cboGrupo.DataSource = consulta.ToList
            End Using
        Catch ex As Exception
            MessageBox.Show(" Erro " & ex.Message & " - " & ex.InnerException.ToString)
        End Try
    End Sub

Usamos a propriedade DisplayMember para exibe o nome do grupo e a propriedade ValueMember que irá retornar o código do grupo via propriedade SelectedValue da combobox.

2- carregaSedes

Carrega a combobox cboLocal com os nomes e códigos das Sedes:

 Private Sub carregaSedes()
        Try
            Using ctx As New Copa2014Entities
                Dim consulta = From local In ctx.Locais
                                     Select local
                cboLocal.DisplayMember = "NomeLocal"
                cboLocal.ValueMember = "LocalId"
                cboLocal.DataSource = consulta.ToList
            End Using
        Catch ex As Exception
            MsgBox(" Erro " & ex.Message)
        End Try
    End Sub

3- carregaSelecoes

Carregamos os controles cboSelecao1 e cboSelecao2 com o nome e id das seleções filtradas pelo grupo selecionado na caixa de combinação cboGrupo dessa forma veremos apenas as seleções do grupo facilitando a seleção.

 Private Sub carregaSelecoes()
        Try
            Using ctx As New Copa2014Entities
                Dim grupoid As Integer = cboGrupo.SelectedValue
                Dim consulta = From selecao In ctx.Selecoes
                                    Where selecao.GrupoId = grupoid
                                     Select selecao
                '//-------------- seleção 1
                cboSelecao1.DisplayMember = "NomeSelecao"
                cboSelecao1.ValueMember = "SelecaoId"
                cboSelecao1.DataSource = consulta.ToList
                '//--------------seleção 2
                cboSelecao2.DisplayMember = "NomeSelecao"
                cboSelecao2.ValueMember = "SelecaoId"
                cboSelecao2.DataSource = consulta.ToList
            End Using
        Catch ex As Exception
            MessageBox.Show(" Erro " & ex.Message & " - " & ex.InnerException.ToString)
        End Try
    End Sub

4- carregaGrid

Para carregar o controle DataGridView e exibir os jogos cadastrados obtemos o valor do código do grupo selecionado na combobox cboGrupo e executamos uma consulta LINQ que filtra os jogos pelo grupo exibindo-os no controle:

 Private Sub carregaGrid()
        Using ctx As New Copa2014Entities
            Try
                Dim grupoid As Integer = cboGrupo.SelectedValue
                Dim jogos = From jg In ctx.Jogos
                                 Where jg.GrupoId = grupoid
                                 Select jg.JogoId, jg.Data, jg.Hora, jg.Locais.NomeLocal, jg.SelecaoId1, jg.SelecaoId2
                dgvJogos.DataSource = jogos.ToList()
                formatGrid()
            Catch ex As Exception
                MessageBox.Show("Erro " + ex.Message, "Erro::Exibir", MessageBoxButtons.OK, MessageBoxIcon.Error)
            End Try
        End Using
    End Sub

As rotinas carregaSelecoes() e carregaGrid() também são chamadas quando houver uma alteração no código do grupo selecionado. Para isso usamos o evento SelectedIndexChanged do controle cboGrupo com o código a seguir:

Private Sub cboGrupo_SelectedIndexChanged(sender As Object, e As EventArgs) Handles cboGrupo.SelectedIndexChanged
        carregaSelecoes()
        carregaGrid()
    End Sub

Da mesma forma usamos o evento SeledtedIndexChanged das combobox cboSelecao1 e cboSelecao2 para que quando houver alteração nas informações das seleções possamos obter a bandeira da seleção e exibi-la nos controles picSelecao1 e picSelecao:

Private Sub cboSelecao1_SelectedIndexChanged(sender As Object, e As EventArgs) Handles cboSelecao1.SelectedIndexChanged
        Dim codigo As Integer = cboSelecao1.SelectedValue
        Using ctx As New Copa2014Entities
            Dim selecao = (From sel In ctx.Selecoes Where sel.SelecaoId = codigo).SingleOrDefault
            If IsNothing(selecao) Then
                MessageBox.Show("Seleção não localizada", "Localizar", MessageBoxButtons.OK, MessageBoxIcon.Information)
                Return
            End If
            picSelecao1.Image = Image.FromFile(selecao.Bandeira)
        End Using
    End Sub

    Private Sub cboSelecao2_SelectedIndexChanged(sender As Object, e As EventArgs) Handles cboSelecao2.SelectedIndexChanged
        Dim codigo As Integer = cboSelecao2.SelectedValue
        Using ctx As New Copa2014Entities
            Dim selecao = (From sel In ctx.Selecoes Where sel.SelecaoId = codigo).SingleOrDefault
            If IsNothing(selecao) Then
                MessageBox.Show("Seleção não localizada", "Localizar", MessageBoxButtons.OK, MessageBoxIcon.Information)
                Return
            End If
            picSelecao2.Image = Image.FromFile(selecao.Bandeira)
        End Using
    End Sub

Localizando, Incluindo, alterando e excluindo jogos

Após selecionar as informações para cada jogo o usuário poderá procurar, incluir, alterar ou excluir um jogo. A implementação do código é feita no evento Click dos botões de comando btnProcurar, btnIncluir, btnAlterar e btnExcluir:

1- Localizando um jogo cadastrado

Private Sub btnProcurar_Click(sender As Object, e As EventArgs) Handles btnProcurar.Click
        Dim codigo As Integer
        If String.IsNullOrEmpty(txtId.Text) Then
            MessageBox.Show("Informe o código do jogo", "Localizar", MessageBoxButtons.OK, MessageBoxIcon.Information)
            Return
        Else
            codigo = Convert.ToInt32(txtId.Text)
        End If
        Try
            Using ctx As New Copa2014Entities
                Dim jogo = (From jog In ctx.Jogos Where jog.JogoId = codigo).SingleOrDefault
                If IsNothing(jogo) Then
                    MessageBox.Show("Jogo não localizado", "Localizar", MessageBoxButtons.OK, MessageBoxIcon.Information)
                    Return
                End If
                dtpData.Value = jogo.Data
                cboHora.Text = jogo.Hora.ToString
                cboGrupo.SelectedValue = jogo.GrupoId
                cboLocal.SelectedValue = jogo.LocalId
                cboSelecao1.SelectedValue = jogo.SelecaoId1
                cboSelecao2.SelectedValue = jogo.SelecaoId2
            End Using
        Catch ex As Exception
            MessageBox.Show("Erro " + ex.Message, "Erro::Localizar", MessageBoxButtons.OK, MessageBoxIcon.Error)
        End Try
    End Sub

Estou apenas repetindo esse código onde após localizar o jogo pelo seu código atualizamos os controles do formulário com o dado da entidade jogo encontrada.

2- Incluir novo Jogo

Private Sub btnIncluir_Click(sender As Object, e As EventArgs) Handles btnIncluir.Click
        Try
            Using ctx As New Copa2014Entities
                Dim jogo As New Jogos
                jogo.Data = dtpData.Value
                jogo.Hora = TimeSpan.Parse(GetHoraValida(cboHora.Text))
                jogo.LocalId = cboLocal.SelectedValue
                jogo.GrupoId = cboGrupo.SelectedValue
                jogo.SelecaoId1 = cboSelecao1.SelectedValue
                jogo.SelecaoId2 = cboSelecao2.SelectedValue
                ctx.Jogos.Add(jogo)
                ctx.SaveChanges()
                MessageBox.Show("Jogo incluído com sucesso : " & cboSelecao1.Text & " x " & cboSelecao2.Text, "Incluir", MessageBoxButtons.OK, MessageBoxIcon.Information)
                cboLocal.SelectedIndex = -1
                dtpData.Focus()
                carregaGrid()
            End Using
        Catch ex As Exception
            MessageBox.Show("Erro " + ex.Message, "Erro::Incluir", MessageBoxButtons.OK, MessageBoxIcon.Error)
        End Try
    End Sub
 

Para incluir um jogo criamos uma instância da entidade Jogos e atribuímos os valores informados pelo usuário nos controles do formulário para as propriedades da entidade; incluímos o objeto no contexto e usamos o método SaveChanges() para persistir as informações no banco de dados.

No código usamos a rotina GetHoraValida() para validar uma hora selecionada na combobox cboHora com o código a seguir:

Private Function GetHoraValida(ByVal hora As String) As String
        Try
            Dim dt As DateTime = DateTime.ParseExact(hora, "HH:mm", Nothing)
            Return hora
        Catch
            Return "00:00"
        End Try
    End Function

3- Alterando um Jogo

Private Sub btnAlterar_Click(sender As Object, e As EventArgs) Handles btnAlterar.Click
        Dim codigo As Integer
        If String.IsNullOrEmpty(txtId.Text) Then
            MessageBox.Show("Informe o código do Jogo", "Alterar", MessageBoxButtons.OK, MessageBoxIcon.Information)
            Return
        Else
            codigo = Convert.ToInt32(txtId.Text)
        End If
        If cboLocal.SelectedIndex = -1 Then
            MessageBox.Show("Selecione o local do jogo", "Alterar", MessageBoxButtons.OK, MessageBoxIcon.Information)
            Return
        End If
        Try
            Using ctx As New Copa2014Entities
                Dim jogo = (From jog In ctx.Jogos Where jog.JogoId = codigo).SingleOrDefault
                If IsNothing(jogo) Then
                    MessageBox.Show("Jogo não localizado", "Localizar", MessageBoxButtons.OK, MessageBoxIcon.Information)
                    Return
                End If
                jogo.Data = dtpData.Value
                jogo.Hora = TimeSpan.Parse(GetHoraValida(cboHora.Text))
                jogo.GrupoId = cboGrupo.SelectedValue
                jogo.LocalId = cboLocal.SelectedValue
                jogo.SelecaoId1 = cboSelecao1.SelectedValue
                jogo.SelecaoId2 = cboSelecao2.SelectedValue
                ctx.SaveChanges()
                carregaGrid()
            End Using
        Catch ex As Exception
            MessageBox.Show("Erro " + ex.Message, "Erro::Alterar", MessageBoxButtons.OK, MessageBoxIcon.Error)
        End Try
    End Sub

A lógica da alteração de um jogo é mesma que já foi exibida anteriormente. Localizamos o jogo pelo seu código via consulta LINQ, atualizamos as propriedades da entidade e persistimos usando SaveChanges.

4- Excluindo um Jogo

Para excluir um jogo localizamos o jogo a ser excluído pelo seu código e usamos o método Remove() do contexto e a seguir o método SaveChanges() para efetivar a exclusão do contexto.

Private Sub btnExcluir_Click(sender As Object, e As EventArgs) Handles btnExcluir.Click
        Dim codigo As Integer
        If String.IsNullOrEmpty(txtId.Text) Then
            MessageBox.Show("Informe o código do Jogo", "Excluir", MessageBoxButtons.OK, MessageBoxIcon.Information)
            Return
        Else
            codigo = Convert.ToInt32(txtId.Text)
        End If
        Try
            Using ctx As New Copa2014Entities
                Dim jogo As Jogos = ctx.Jogos.First(Function(jg) jg.JogoId = codigo)
                ctx.Jogos.Remove(jogo)
                ctx.SaveChanges()
                carregaGrid()
            End Using
        Catch ex As Exception
            MessageBox.Show("Erro " + ex.Message, "Erro::Excluir", MessageBoxButtons.OK, MessageBoxIcon.Error)
        End Try
    End Sub

Para exibir os valores de um jogo no formulário, selecionado uma linha no controle DataGridView, usamos o evento CellClick de forma a obter os valores e exibir os mesmos no formulário:

 Private Sub dgvJogos_CellClick(sender As Object, e As DataGridViewCellEventArgs) Handles dgvJogos.CellClick
        Try
            If dgvJogos.Rows(e.RowIndex).Cells(0).Value <> Nothing Then
                Dim codigo As Integer = dgvJogos.Rows(e.RowIndex).Cells(0).Value
                Try
                    Using ctx As New Copa2014Entities
                        Dim jogo = (From jog In ctx.Jogos Where jog.JogoId = codigo).SingleOrDefault
                        txtId.Text = jogo.JogoId
                        dtpData.Value = jogo.Data
                        cboHora.Text = jogo.Hora.ToString
                        cboGrupo.SelectedValue = jogo.GrupoId
                        cboLocal.SelectedValue = IIf(jogo.LocalId IsNot Nothing, jogo.LocalId, 0)
                        cboSelecao1.SelectedValue = jogo.SelecaoId1
                        cboSelecao2.SelectedValue = jogo.SelecaoId2
                    End Using
                Catch ex As Exception
                    MessageBox.Show("Erro " + ex.Message, "Erro::Localizar", MessageBoxButtons.OK, MessageBoxIcon.Error)
                End Try
            End If
        Catch ex As Exception
        End Try
    End Sub

Aqui após localizar o jogo via consulta LINQ pelo código do jogo que é obtido a partir da primeira célula (Cells(0)), obtemos o valores da entidade e os atribuímos aos controles do formulário.

Exibindo os jogos por grupo e fazendo simulações

Após cadastrar os jogos de todos os grupos podemos exibi-los por grupo e fazer simulações informando valores para os resultados dos mesmos.

No formulário principal temos os botões de comando para os oito grupos de A até a H, de forma que basta clicar no botão do respectivo grupo para exibir os jogos cadastrados para o grupo.

Vejamos o código onde tratamos o evento de cada botão para exibir os jogos do grupo:

 Private Sub btnGA_Click(sender As Object, e As EventArgs) Handles btnGA.Click, btnGB.Click, btnGC.Click, 
btnGD.Click, btnGE.Click, btnGF.Click, btnGG.Click, btnGH.Click, btnOitavas.Click, btnQuartas.Click, 
btnSemi.Click, btnFinal.Click
        Dim botao As Button
        botao = CType(sender, Button)
        Select Case botao.Name
            Case "btnGA"
                grpJogos.Visible = True
                grpClassificacao.Visible = True
                btnClassificacao.Visible = True
                preencheGrid(1, botao.Tag)
            Case "btnGB"
                grpJogos.Visible = True
                grpClassificacao.Visible = True
                btnClassificacao.Visible = True
                preencheGrid(2, botao.Tag)
            Case "btnGC"
                grpJogos.Visible = True
                grpClassificacao.Visible = True
                btnClassificacao.Visible = True
                preencheGrid(3, botao.Tag)
            Case "btnGD"
                grpJogos.Visible = True
                grpClassificacao.Visible = True
                btnClassificacao.Visible = True
                preencheGrid(4, botao.Tag)
            Case "btnGE"
                grpJogos.Visible = True
                grpClassificacao.Visible = True
                btnClassificacao.Visible = True
                preencheGrid(5, botao.Tag)
            Case "btnGF"
                grpJogos.Visible = True
                grpClassificacao.Visible = True
                btnClassificacao.Visible = True
                preencheGrid(6, botao.Tag)
            Case "btnGG"
                grpJogos.Visible = True
                grpClassificacao.Visible = True
                btnClassificacao.Visible = True
                preencheGrid(7, botao.Tag)
            Case "btnGH"
                grpJogos.Visible = True
                grpClassificacao.Visible = True
                btnClassificacao.Visible = True
                preencheGrid(8, botao.Tag)
            Case "btnOitavas"
                My.Forms.Form_Oitavas.ShowDialog()
            Case "btnQuartas"
                My.Forms.Form_Quartas.ShowDialog()
            Case "btnSemi"
                My.Forms.Form_Semi.ShowDialog()
            Case "btnFinal"
                My.Forms.Form_Final.ShowDialog()
        End Select
    End Sub

Notou que eu estou tratando todos os eventos Click de cada um dos botões em um único código de manipulador de eventos ?

Após atribuir o evento Click de cada botão criamos uma instância de um objeto Button e a seguir usamos o objeto Sender. Este objeto é passando ao evento pelo VB.NET e ele trata a referência ao objeto que disparou o evento basta então obter qual o controle que disparou o evento via objeto Sender . Para isto temos que fazer uma conversão de tipo de dados forçada (um casting).

        Dim botao As Button
        botao = CType(sender, Button)

Usando um Select Case verificamos qual o nome do botão foi clicado e definimos o código correspondente à ação desejada:

 Select Case botao.Name
            Case "btnGA"
             ...
            Case "btnFinal"
                ...
 End Select

Após tornar os controles visíveis chamamos a rotina preencheGrid() que possui o seguinte código:

Private Sub preencheGrid(ByVal grupo As Integer, ByVal btn As String)
        grupoAtual = grupo
        grpJogos.Text = " Jogos - Grupo " & btn
        grpClassificacao.Text = " Classificacao - Grupo " & btn
        Dim lblDatas() As Label = New Label() {lblData1, lblData2, lblData3, lblData4, lblData5, lblData6}
        Dim lblHoras() As Label = New Label() {lblHora1, lblHora2, lblHora3, lblHora4, lblHora5, lblHora6}
        Dim lblSelecoes1() As Label = New Label() {lblSelecao11, lblSelecao12, lblSelecao13, lblSelecao14, lblSelecao15, lblSelecao16}
        Dim picBandeiras1() As PictureBox = New PictureBox() {picBandeiraSelecao11, picBandeiraSelecao12, picBandeiraSelecao13, picBandeiraSelecao14,
 picBandeiraSelecao15, picBandeiraSelecao16}
        Dim txtGol1s() As TextBox = New TextBox() {txtGol11, txtGol12, txtGol13, txtGol14, txtGol15, txtGol16}
        Dim txtGol2s() As TextBox = New TextBox() {txtGol21, txtGol22, txtGol23, txtGol24, txtGol25, txtGol26}
        Dim picBandeiras2() As PictureBox = New PictureBox() {picBandeiraSelecao21, picBandeiraSelecao22, picBandeiraSelecao23, picBandeiraSelecao24,
 picBandeiraSelecao25, picBandeiraSelecao26}
        Dim lblSelecoes2() As Label = New Label() {lblSelecao21, lblSelecao22, lblSelecao23, lblSelecao24, lblSelecao25, lblSelecao26}
        Dim i As Integer = 0
        Using ctx As New Copa2014Entities
            Try
                Dim jogos = From jg In ctx.Jogos
                            Where jg.GrupoId = grupoAtual
                            Select jg
                If jogos.Count = 6 Then
                    For Each jogo In jogos
                        'atualiza os controles do formulário
                        lblDatas(i).Text = jogo.Data
                        lblHoras(i).Text = jogo.Hora.ToString
                        lblSelecoes1(i).Text = jogo.Selecoes.NomeSelecao
                        picBandeiras1(i).Image = exibeBandeira(jogo.Selecoes.Bandeira)
                        txtGol1s(i).Text = jogo.Gol1
                        txtGol2s(i).Text = jogo.Gol2
                        picBandeiras2(i).Image = exibeBandeira(jogo.Selecoes1.Bandeira)
                        lblSelecoes2(i).Text = jogo.Selecoes1.NomeSelecao
                        i = i + 1
                    Next
                Else
                    grpJogos.Visible = False
                    grpClassificacao.Visible = False
                    btnClassificacao.Visible = False
                    MessageBox.Show("Não há jogos cadastrados para este grupo. Cadastre os jogos antes...")
                End If
            Catch ex As Exception
                MessageBox.Show("Erro " + ex.Message, "Erro:: ", MessageBoxButtons.OK, MessageBoxIcon.Error)
            End Try
        End Using
    End Sub

Este código  utiliza o recurso de criar um array de controles (como o VB6 fazia nativamente). O que fizemos aqui foi definir um array para cada tipo de controle que usamos no formulário. Exemplo:

Para acessar um determinado objeto basta usar o seu índice no array (começa com o valor zero). Assim podemos percorrer o array de controles usando um laço for Each/next, conforme fizemos, e assim acessar todos os controles do array que estão definidos no formulário:

                     For Each jogo In jogos
                    
   'atualiza os controles do formulário
                        lblDatas(i).Text = jogo.Data
                        lblHoras(i).Text = jogo.Hora.ToString
                        lblSelecoes1(i).Text = jogo.Selecoes.NomeSelecao
                        picBandeiras1(i).Image = exibeBandeira(jogo.Selecoes.Bandeira)
                        txtGol1s(i).Text = jogo.Gol1
                        txtGol2s(i).Text = jogo.Gol2
                        picBandeiras2(i).Image = exibeBandeira(jogo.Selecoes1.Bandeira)
                        lblSelecoes2(i).Text = jogo.Selecoes1.NomeSelecao
                        i = i + 1
                    Next

Fazer isso da forma tradicional seria um pesadelo.

Para exibir a imagem da bandeira de cada seleção usamos a rotina exibeBandeira com o seguinte código:

Private Function exibeBandeira(ByVal nomeArquivo As String) As Bitmap
        Try
            Dim bm As New Bitmap(nomeArquivo)
            Return bm
        Catch ex As Exception
            Throw ex
        End Try
    End Function

O código do botão de comando - Ver / Atualizar Classificação - é visto abaixo e chama as rotinas atualizaJogos(), atualizaclassificacao() e exibeClassificacao(). Esse código pode ser disparado após atualizarmos os resultados dos jogos ou para atualizar a classificação do grupo:

Private Sub btnClassificacao_Click(sender As Object, e As EventArgs) Handles btnClassificacao.Click
        atualizaJogos(grupoAtual)
        atualizaClassificacao(grupoAtual)
        exibeClassificacao(grupoAtual)
    End Sub

O método atualizaJogos() recebe o código do grupo como parâmetro e permite atualizar o resultado dos jogos:

Private Sub atualizaJogos(ByVal grupo As Integer)
        Dim txtGol1s() As TextBox = New TextBox() {txtGol11, txtGol12, txtGol13, txtGol14, txtGol15, txtGol16}
        Dim txtGol2s() As TextBox = New TextBox() {txtGol21, txtGol22, txtGol23, txtGol24, txtGol25, txtGol26}
        grupoAtual = grupo
        Dim i As Integer = 0
        Using ctx As New Copa2014Entities
            Try
                Dim jogos = From jg In ctx.Jogos
                            Where jg.GrupoId = grupoAtual
                            Select jg
                If jogos.Count = 6 Then
                    For Each jogo In jogos.ToList
                        'atualiza os controles do formulário
                        jogo.Gol1 = txtGol1s(i).Text
                        jogo.Gol2 = txtGol2s(i).Text
                        ctx.SaveChanges()
                        i = i + 1
                    Next
                Else
                    MessageBox.Show("Não há jogos cadastrados para este grupo. Cadastre os jogos antes...")
                End If
            Catch ex As Exception
                MessageBox.Show("Erro " + ex.Message, "Erro:: ", MessageBoxButtons.OK, MessageBoxIcon.Error)
            End Try
        End Using
    End Sub

Para atualizar a classificação precisamos declarar as variáveis usadas para computar a classificação no início do formulário:

    Dim grupoAtual As Integer = 1
    Dim selid As Integer
    Dim jgs As Integer
    Dim pts As Integer
    Dim vit As Integer
    Dim emp As Integer
    Dim der As Integer
    Dim gp As Integer
    Dim gc As Integer
    Dim sg As Integer

O código que atualiza a classificação percorre os  jogos para cada seleção verificando as vitórias, derrotas e empates e calculando os gols pro e gols contra e saldo de gols:

Nota: O critério usado é o definido pela FIFA que pode ser visto neste link: http://copadomundo.uol.com.br/regulamento/

 Private Sub atualizaClassificacao(ByVal grupoAtual As Integer)
        Using ctx As New Copa2014Entities
            Try
                Dim jogos = From jg In ctx.Jogos
                            Where jg.GrupoId = grupoAtual
                            Select jg
                Dim selecoes = From sel In ctx.Selecoes
                       Where sel.GrupoId = grupoAtual
                       Select sel
                For Each selecao In selecoes.ToList()
                    selid = selecao.SelecaoId
                    'zera valores para inicio da contagem
                    pts = 0
                    sg = 0
                    gp = 0
                    gc = 0
                    jgs = 0
                    vit = 0
                    emp = 0
                    der = 0
                    For Each jogo In jogos.ToList
                        If jogo.SelecaoId1 = selid Then
                            'incrementa jogos
                            jgs = jgs + 1
                            'calcula vitoria , empates e derrotas
                            If jogo.Gol1 = jogo.Gol2 Then
                                emp = emp + 1
                                gp = gp + jogo.Gol1
                                gc = gc + jogo.Gol2
                            ElseIf jogo.Gol1 > jogo.Gol2 Then
                                vit = vit + 1
                                gp = gp + jogo.Gol1
                                gc = gc + jogo.Gol2
                            ElseIf jogo.Gol1 < jogo.Gol2 Then
                                der = der + 1
                                gp = gp + jogo.Gol1
                                gc = gc + jogo.Gol2
                            End If
                        ElseIf jogo.SelecaoId2 = selid Then
                            'incrementa jogos
                            jgs = jgs + 1
                            'calcula vitoria , empates e derrotas
                            If jogo.Gol1 = jogo.Gol2 Then
                                emp = emp + 1
                                gp = gp + jogo.Gol1
                                gc = gc + jogo.Gol2
                            ElseIf jogo.Gol1 > jogo.Gol2 Then
                                der = der + 1
                                gp = gp + jogo.Gol2
                                gc = gc + jogo.Gol1
                            ElseIf jogo.Gol1 < jogo.Gol2 Then
                                vit = vit + 1
                                gp = gp + jogo.Gol2
                                gc = gc + jogo.Gol1
                            End If
                        End If
                    Next
                    'calcula pontos e salgo de gols
                    pts = vit * 3 + emp * 1
                    sg = gp - gc
                    'atualiza classificacao
                    InserirAtualizarDadosClassificacao(grupoAtual, selid)
                Next
                'exibe classificacao
                exibeClassificacao(grupoAtual)
            Catch ex As Exception
                MessageBox.Show("Erro " + ex.Message, "Erro:: ", MessageBoxButtons.OK, MessageBoxIcon.Error)
            End Try
        End Using
    End Sub

No código acima temos a chamada da rotina inserirAtualizarDadosClassificacao que atualiza as entidades com os novos valores salvando-os no banco de dados:

 Private Sub InserirAtualizarDadosClassificacao(ByVal grupoId As Integer, ByVal selecaoid As Integer)
        Try
            Using ctx As New Copa2014Entities
                Dim classif = (From cla In ctx.Classificacao Where cla.SelecaoId = selecaoid).SingleOrDefault
                If IsNothing(classif) Then
                    Dim classificacao As New Classificacao
                    classificacao.SelecaoId = selecaoid
                    classificacao.GrupoId = grupoId
                    classificacao.Pontos = pts
                    classificacao.Jogos = jgs
                    classificacao.Vitorias = vit
                    classificacao.Empates = emp
                    classificacao.Derrotas = der
                    classificacao.GolPro = gp
                    classificacao.GolContra = gc
                    classificacao.SaldoGols = sg
                    ctx.Classificacao.Add(classificacao)
                    ctx.SaveChanges()
                Else
                    Try
                        classif.SelecaoId = selecaoid
                        classif.GrupoId = grupoId
                        classif.Pontos = pts
                        classif.Jogos = jgs
                        classif.Vitorias = vit
                        classif.Empates = emp
                        classif.Derrotas = der
                        classif.GolPro = gp
                        classif.GolContra = gc
                        classif.SaldoGols = sg
                        ctx.SaveChanges()
                    Catch ex As Exception
                        MessageBox.Show("Erro " + ex.Message, "Erro::Alterar", MessageBoxButtons.OK, MessageBoxIcon.Error)
                    End Try
                End If
            End Using
        Catch ex As Exception
            MessageBox.Show("Erro " + ex.Message, "Erro::Incluir/Atualizar", MessageBoxButtons.OK, MessageBoxIcon.Error)
        End Try
    End Sub

Finalmente a classificação é exibida no controle DataGridView e o grid é formatado pela rotina formataGridView():

 Private Sub exibeClassificacao(ByVal grupo As Integer)
        Using ctx As New Copa2014Entities
            Try
                dgvClassificacao.DataSource = Nothing
                Dim classificacao = From clsf In ctx.Classificacao
                                    Where clsf.GrupoId = grupoAtual
                                    Order By clsf.Pontos Descending, clsf.SaldoGols Descending, clsf.GolPro Descending
                                    Select clsf.Selecoes.NomeSelecao, clsf.Pontos, clsf.Jogos, clsf.Vitorias, clsf.Empates,
 clsf.Derrotas, clsf.GolPro, clsf.GolContra, clsf.SaldoGols
                dgvClassificacao.DataSource = classificacao.ToList
                formataGridView()
            Catch ex As Exception
                MessageBox.Show("Erro " + ex.Message, "Erro:: ", MessageBoxButtons.OK, MessageBoxIcon.Error)
            End Try
        End Using
    End Sub

Rotina fomataGridView() realiza a formatação do grid usando diversas propriedades do controle DataGridView:

 Private Sub formataGridView()
        With dgvClassificacao
            .AutoGenerateColumns = False
            .RowHeadersVisible = False
            .AutoSizeRowsMode = DataGridViewAutoSizeRowsMode.DisplayedCellsExceptHeaders
            .ColumnHeadersBorderStyle = DataGridViewHeaderBorderStyle.Single
            'altera a cor das linhas alternadas no grid
            .RowsDefaultCellStyle.BackColor = Color.White
            .AlternatingRowsDefaultCellStyle.BackColor = Color.YellowGreen
            'altera o nome das colunas
            .Columns(0).HeaderText = "Classificação"
            .Columns(1).HeaderText = "P"
            .Columns(2).HeaderText = "J"
            .Columns(3).HeaderText = "V"
            .Columns(4).HeaderText = "E"
            .Columns(5).HeaderText = "D"
            .Columns(6).HeaderText = "GP"
            .Columns(7).HeaderText = "GC"
            .Columns(8).HeaderText = "SG"
            'largura colunas
            .Columns(0).Width = 150
            .Columns(1).Width = 50
            .Columns(2).Width = 50
            .Columns(3).Width = 50
            .Columns(4).Width = 50
            .Columns(5).Width = 50
            .Columns(6).Width = 50
            .Columns(7).Width = 50
            .Columns(8).Width = 50
            'seleciona a linha inteira
            .SelectionMode = DataGridViewSelectionMode.FullRowSelect
            'não permite seleção de multiplas linhas
            .MultiSelect = False
            ' exibe nulos formatados
            .DefaultCellStyle.NullValue = " - "
            'permite que o texto maior que célula não seja truncado
            .DefaultCellStyle.WrapMode = DataGridViewTriState.True
        End With
    End Sub

 

Para ocultar os controles temos o código do botão btnInicio - INICIO :

Private Sub btnInicio_Click(sender As Object, e As EventArgs) Handles btnInicio.Click
        grpClassificacao.Visible = False
        grpJogos.Visible = False
        btnClassificacao.Visible = False
    End Sub

No próximo artigo vou apresentar os formulários para cadastros das jogos da oitava, quarta, da semi e da final e liberar o código fonte do programa.

Salmos 19:1 Os céus proclamam a glória de Deus e o firmamento anuncia a obra das suas mãos.

Salmos 19:2 Um dia faz declaração a outro dia, e uma noite revela conhecimento a outra noite.

Salmos 19:3 Não há fala, nem palavras; não se lhes ouve a voz.


Veja os Destaques e novidades do SUPER DVD VB (sempre atualizado) : clique e confira !

Quer migrar para o VB .NET ?

Veja mais sistemas completos para a plataforma .NET no Super DVD .NET , confira...

Quer aprender C# ??

Chegou o Super DVD C# com exclusivo material de suporte e vídeo aulas com curso básico sobre C#
 

   Gostou ?   Compartilhe no Facebook    Compartilhe no Twitter

Referências:


José Carlos Macoratti