How to update a Dropdownlist without refreshing the page

Asked

Viewed 1,201 times

4

I have a State Dropdown, and a City Dropdown, and a zip code field, which is making use of the mail online API, when I put a zip code, my system checks whether the city already exists in the database, and if it has not been added. so far so good, the problem is that I have a dropdown that brings the cities that were registered until the screen update, but when I type the zip code, and it searches the city, that when it does not exist and inserts the new one, it does not update my Dropdown with the cities, not displaying the 'new' city, but if I refresh the whole page, it displays this new city. I wanted an option so that when being inserted into the bank this new city, my dropdown will be updated as well.

Javascript Utilizado:

<script>
    $(document).ready(function () {
        $("#cep").blur(function () {
            var cepValue = $(cep).val();
            $.ajax({
                type: 'POST',
                url: 'RetornaEndereco',
                data: { cep: cepValue },
                dataType: 'json',
                success: function (data) {
                    $('#bairro').val(data.bairro);
                    $('#endereco').val(data.end);
                    $('#cidade').val(data.cidade);
                    $('#estado').val(data.uf);
                },
                error: function (data) {
                    alert('Error' + data);
                }
            });
        });
    });
</script>

Controller

public JsonResult RetornaEndereco(string cep)
{
    var valor = Regex.Replace(cep, "[^0-9]", "");
    var ws = new WSCorreios.AtendeClienteClient();
    var resposta = ws.consultaCEP(valor);
    try
    {
        System.Console.WriteLine();
        System.Console.WriteLine("Endereço: {0}", resposta.end);
        System.Console.WriteLine("Bairro: {0}", resposta.bairro);
        System.Console.WriteLine("Cidade: {0}", resposta.cidade);
        System.Console.WriteLine("Estado: {0}", resposta.uf);
    }
    catch (Exception ex)
    {
        return Json("Erro ao efetuar busca do CEP: {0}", ex.Message);
    }

   Estado estado = (from u in db.Estados where u.Sigla == resposta.uf select u).SingleOrDefault();//Busca no banco pelo Estado

    Cidade iDCidade = (from u in db.Cidades where u.Nome == resposta.cidade && u.EstadoID == estado.EstadoID select u).SingleOrDefault();//Busca no banco pela cidade que está no mesmo estado
    Cidade levaCidade = new Cidade();
    if (iDCidade == null)//Se a cidade não estiver cadastrada, insere uma nova cidade. 
    {
        Cidade cidade = new Cidade();
        cidade.Nome = resposta.cidade;
        cidade.EstadoID = estado.EstadoID;
        db.Cidades.Add(cidade);
        db.SaveChanges();
        levaCidade.CidadeID = cidade.CidadeID;//Pega o ID da cidade cadastrada
        levaCidade.EstadoID = cidade.EstadoID;//pega o id do estado selecionado
    }
    else
    {
        Cidade cidade = new Cidade();
        cidade.Nome = resposta.cidade;
        cidade.EstadoID = estado.EstadoID;
        levaCidade.CidadeID = iDCidade.CidadeID;//Pega o ID da cidade cadastrada
        levaCidade.EstadoID = estado.EstadoID;//pega o id do estado selecionado
    }
    Endereco levarEndereco = new Endereco();//Cria o objeto para ser transportado pelo Json
    levarEndereco.CidadeID = levaCidade.CidadeID;
    levarEndereco.Numero = levaCidade.EstadoID;//Passando o id do estado na variavel numero para alterar no json
    levarEndereco.Bairro = resposta.bairro;
    levarEndereco.Descricao = resposta.end;
    ViewBag.CidadeID = new SelectList(db.Cidades, "CidadeID", "Nome", levarEndereco.CidadeID);

     return Json(levarEndereco);
}

Dropdownlist

 <div class="form-group">
    @Html.LabelFor(model => model.CidadeID, "Estado", htmlAttributes: new { @class = "control-label col-md-2" })
    <div class="col-md-10">
        @Html.DropDownList("CidadeID", null, htmlAttributes: new { @class = "form-control", id = "Cidade", })
        @Html.ValidationMessageFor(model => model.CidadeID, "", new { @class = "text-danger" })
    </div>
</div
  • Good morning can share some code from both html and c#?

  • Good morning @Fabiosilvalima I was so tired last night, I didn’t even put the code, it was bad. I updated the question. thanks

  • You need a function that reloads dropdown content via ajax after completing the Return Controller Method

  • This is because in the web application, datasource Binding is done only on page loading and not in real time (Unless of course, you implement this at hand using AJAX or Socket/Signalr). To get the updated data just make an AJAX request for a new method that returns the updated JSON cities... But one council, Brazil has 5570 cities, it is not easier to register all of them at once ?

  • Here are links with SQL to register all cities at once: - http://samus.com.br/web/site/artigo-todas_cites_do_brasil_e_com_acentos (missing 6 cities) - https://chandez/Cidades-IBGE (missing 5 cities)

1 answer

1

-- Edited to improve response and add code.

In your Json you need to access the function that saves your new city and then return a complete list of all cities, including the new city added.

After that, in Json’s 'Success' you need to change the "date" of your Lect2. With this it creates all of Select2 again, so you need to pass on the desired options like placeholder, Theme and etc ...

Code:

$.post('url do teu método', {post}).success(function(response) {    
    // o método precisa retornar uma lista atualizada das cidades
    // como array dentro do response (response.data)
    // o response == ao return do teu método

    // recebe os dados retornados
    let data = response.data;

    // seta o value do select
    $('seu select').select2({
        placeholder: 'Selecione ...',
        data: data,
        allowClear: 'true',
    });
});

But remember, Select2 does not accept an object as 'data', so if your application returns an object instead of an array, you need to transform it first:

let arrayData = [];
Object.keys(response.data).forEach(id => {
    arrayData.push({
        id: id,
        text: response.data[id],
    });
});

Then in the "date" of Select2 you pass the Data array.

However, another solution not so elegant if you do not want or do not have so much familiarity in consulting the database, is simply add the new option with "append" inside select and activate a "change" event in select.

$('seu select').append($('<option>', {
    value: 'o id da nova cidade',
    text: 'a descrição da nova cidade'
})).trigger('change');
  • How would he do that?

  • 1

    @Cypherpotato I updated the answer, now it should be clear :)

Browser other questions tagged

You are not signed in. Login or sign up in order to post.