Django formset, calculate total with Jquery

Asked

Viewed 405 times

0

I have my order items being displayed with formset, the quantity and price columns are editable. I’m having trouble calculating the total after changing the price or the quantity. I can identify the entered value by pressing enter, but how could I get the price to calculate the total and update this value in the total column? When loading the order, the total is being calculated in the class method, but to edit, it would be better to do the calculation in the client without having to make a request to the server.

{% load widget_tweaks %}

{{ formset.management_form }}
<div class="table-responsive">
    <table class="table">
        <thead>
            <th>Código</th>
            <th>Descrição</th>
            <th style="width: 10%;">Quantidade</th>
            <th>Preço</th>
            <th>Valor total</th>
            <th>Ação</th>
            <tbody>
                {% for form in formset %}
                <tr>
                    <td>{{ form.instance.produto.pk }}</td>
                    <td>{{ form.instance.produto }}</td>
                    <td>{% render_field form.quantidade class='form-control quantidade' %}</td>
                    <td>{% render_field form.preco class='form-control preco' %}</td>
                    <td>{{ form.instance.get_valorTotal }}</td>
                    <td class="text-center">
                            <button value="on" type="submit" name="{{ form.DELETE.html_name }}" class="btn btn-danger btn-sm">
                            <span class="glyphicon glyphicon-trash"></span> Excluir</button>
                            {{ form.id }}
                    </td>
                </tr>
                {% endfor %}
            </tbody>
        </thead>
    </table>
</div>    
<script>
$(document).ready(function(){
    $(".quantidade").keydown(function(e){
        if (e.which==13) {
            alert($(this).val());
            alert($(this).parent().next('td').html());
            return false;
        }
    });

});
</script> 

After implementing oninput (Jessika credits):

<input id="id_form-TOTAL_FORMS" name="form-TOTAL_FORMS" type="hidden" value="4"><input id="id_form-INITIAL_FORMS" name="form-INITIAL_FORMS" type="hidden" value="4"><input id="id_form-MIN_NUM_FORMS" name="form-MIN_NUM_FORMS" type="hidden" value="0"><input id="id_form-MAX_NUM_FORMS" name="form-MAX_NUM_FORMS" type="hidden" value="1000">
<div class="table-responsive">
    <table class="table">
        <thead>
            <tr><th>Código</th>
            <th>Descrição</th>
            <th style="width: 10%;">Quantidade</th>
            <th>Preço</th>
            <th>Valor total</th>
            <th>Ação</th>
            </tr></thead><tbody>

                <tr>
                    <td>1</td>
                    <td>Processador I7</td>
                    <td><input class="form-control quantidade" id="id_form-0-quantidade" min="0" name="form-0-quantidade" oninput="atualizarDinamico()" type="number" value="1"></td>
                    <td><input class="form-control preco" id="id_form-0-preco" name="form-0-preco" step="0.01" type="number" value="1900.00"></td>
                    <td>1900.00</td>
                    <td class="text-center">
                            <button value="on" type="submit" name="form-0-DELETE" class="btn btn-danger btn-sm">
                            <span class="glyphicon glyphicon-trash"></span> Excluir</button>
                            <input id="id_form-0-id" name="form-0-id" type="hidden" value="6">
                    </td>
                </tr>

                <tr>
                    <td>6</td>
                    <td>Teclado Dell</td>
                    <td><input class="form-control quantidade" id="id_form-1-quantidade" min="0" name="form-1-quantidade" oninput="atualizarDinamico()" type="number" value="1"></td>
                    <td><input class="form-control preco" id="id_form-1-preco" name="form-1-preco" step="0.01" type="number" value="150.00"></td>
                    <td>150.00</td>
                    <td class="text-center">
                            <button value="on" type="submit" name="form-1-DELETE" class="btn btn-danger btn-sm">
                            <span class="glyphicon glyphicon-trash"></span> Excluir</button>
                            <input id="id_form-1-id" name="form-1-id" type="hidden" value="7">
                    </td>
                </tr>

                <tr>
                    <td>5</td>
                    <td>Mouse Logitech XPTO</td>
                    <td><input class="form-control quantidade" id="id_form-2-quantidade" min="0" name="form-2-quantidade" oninput="atualizarDinamico()" type="number" value="1"></td>
                    <td><input class="form-control preco" id="id_form-2-preco" name="form-2-preco" step="0.01" type="number" value="180.00"></td>
                    <td>180.00</td>
                    <td class="text-center">
                            <button value="on" type="submit" name="form-2-DELETE" class="btn btn-danger btn-sm">
                            <span class="glyphicon glyphicon-trash"></span> Excluir</button>
                            <input id="id_form-2-id" name="form-2-id" type="hidden" value="8">
                    </td>
                </tr>

                <tr>
                    <td>3</td>
                    <td>iPhone 6S</td>
                    <td><input class="form-control quantidade" id="id_form-3-quantidade" min="0" name="form-3-quantidade" oninput="atualizarDinamico()" type="number" value="1"></td>
                    <td><input class="form-control preco" id="id_form-3-preco" name="form-3-preco" step="0.01" type="number" value="3500.00"></td>
                    <td>3500.00</td>
                    <td class="text-center">
                            <button value="on" type="submit" name="form-3-DELETE" class="btn btn-danger btn-sm">
                            <span class="glyphicon glyphicon-trash"></span> Excluir</button>
                            <input id="id_form-3-id" name="form-3-id" type="hidden" value="9">
                    </td>
                </tr>

            </tbody>

    </table>
</div>    
<link rel="stylesheet" href="https://ajax.googleapis.com/ajax/libs/jqueryui/1.11.4/themes/smoothness/jquery-ui.css">
<script src="https://ajax.googleapis.com/ajax/libs/jqueryui/1.11.4/jquery-ui.min.js"></script>
<script>
    function atualizarDinamico(object){
        var pos = object.indexOf("-")
        var indice = object.substr(pos+1, 1);

        var quantidade = $('#id_form-' + indice + '-quantidade').val();
        var preco = $('#id_form-' + indice + '-preco').val();

        console.log(quantidade);
        console.log(preco);
        console.log(object);

        console.log(parseFloat(quantidade) * parseFloat(preco));

        $('#total').val(parseFloat(quantidade) * parseFloat(preco)); 
    }
</script>

To update the total, I’m trying this way, but I’m not getting.

$('#id_form-' + indice + '-preco').parent().text(parseInt(quantidade) * parseFloat(preco));

1 answer

1


$('#t1').on('input', function() {
    atualizarTotal();
});
$('#t2').on('input', function() {
    atualizarTotal();
});

function atualizarTotal(){
		valorQnt = $('#t1').val();
    valorPreco = $('#t2').val();
    $('#total').val(parseInt(valorQnt) * parseInt(valorPreco));
}
<p>Preço</p>
<input id="t1" value='1'>
<p>Quantidade</p>
<input id="t2" value='1'>
<p>Total</p>
<input id="total" value='1'>

<h2>Exemplo dinamico</h2>
<p>Preço</p>
<input id="d1" value='1' oninput="atualizarDinamico('d1','d2','totalD')">
<p>Quantidade</p>
<input id="d2" value='1' oninput="atualizarDinamico('d1','d2','totalD')">
<p>Total</p>
<input id="totalD" value='1' oninput="atualizarDinamico('d1','d2','totalD')">

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>

<script>

function atualizarDinamico(preco,qnt,total){
		valorQnt = $("#"+preco).val();
    valorPreco = $("#"+qnt).val();
    $("#"+total).val(parseInt(valorQnt) * parseInt(valorPreco));
}

</script>

I made an example to help you, the idea is the following: every time the price and quantity inputs are changed it is called the update functionTotal to update the value of the total.

<input id="id_form-TOTAL_FORMS" name="form-TOTAL_FORMS" type="hidden" value="4"><input id="id_form-INITIAL_FORMS" name="form-INITIAL_FORMS" type="hidden" value="4"><input id="id_form-MIN_NUM_FORMS" name="form-MIN_NUM_FORMS" type="hidden" value="0"><input id="id_form-MAX_NUM_FORMS" name="form-MAX_NUM_FORMS" type="hidden" value="1000">
<div class="table-responsive">
    <table class="table">
        <thead>
            <tr><th>Código</th>
            <th>Descrição</th>
            <th style="width: 10%;">Quantidade</th>
            <th>Preço</th>
            <th>Valor total</th>
            <th>Ação</th>
            </tr></thead><tbody>

                <tr>
                    <td>1</td>
                    <td>Processador I7</td>
                    <td><input class="form-control quantidade" id="id_form-0-quantidade" min="0" name="form-0-quantidade" oninput="atualizarDinamico(this)" type="number" value="1"></td>
                    <td><input class="form-control preco" id="id_form-0-preco" oninput="atualizarDinamico(this)" name="form-0-preco" step="0.01" type="number" value="1900.00"></td>
                    <td><span id="total-0">1900.00</span></td>
                    <td class="text-center">
                            <button value="on" type="submit" name="form-0-DELETE" class="btn btn-danger btn-sm">
                            <span class="glyphicon glyphicon-trash"></span> Excluir</button>
                            <input id="id_form-0-id" name="form-0-id" type="hidden" value="6">
                    </td>
                </tr>

                <tr>
                    <td>6</td>
                    <td>Teclado Dell</td>
                    <td><input class="form-control quantidade" id="id_form-1-quantidade" min="0" name="form-1-quantidade" oninput="atualizarDinamico(this)" type="number" value="1"></td>
                    <td><input class="form-control preco" id="id_form-1-preco" oninput="atualizarDinamico(this)" name="form-1-preco" step="0.01" type="number" value="150.00"></td>
                    <td><span id="total-1">150.00</span></td>
                    <td class="text-center">
                            <button value="on" type="submit" name="form-1-DELETE" class="btn btn-danger btn-sm">
                            <span class="glyphicon glyphicon-trash"></span> Excluir</button>
                            <input id="id_form-1-id" name="form-1-id" type="hidden" value="7">
                    </td>
                </tr>

                <tr>
                    <td>5</td>
                    <td>Mouse Logitech XPTO</td>
                    <td><input class="form-control quantidade" id="id_form-2-quantidade" min="0" name="form-2-quantidade" oninput="atualizarDinamico(this)" type="number" value="1"></td>
                    <td><input class="form-control preco" id="id_form-2-preco" oninput="atualizarDinamico(this)" name="form-2-preco" step="0.01" type="number" value="180.00"></td>
                    <td><span id="total-2">180.00</span></td>
                    <td class="text-center">
                            <button value="on" type="submit" name="form-2-DELETE" class="btn btn-danger btn-sm">
                            <span class="glyphicon glyphicon-trash"></span> Excluir</button>
                            <input id="id_form-2-id" name="form-2-id" type="hidden" value="8">
                    </td>
                </tr>

                <tr>
                    <td>3</td>
                    <td>iPhone 6S</td>
                    <td><input class="form-control quantidade" id="id_form-3-quantidade" min="0" name="form-3-quantidade" oninput="atualizarDinamico(this)" type="number" value="1"></td>
                    <td><input class="form-control preco" id="id_form-3-preco" oninput="atualizarDinamico(this)" name="form-3-preco" step="0.01" type="number" value="3500.00"></td>
                    <td><span id="total-3">3500.00</span></td>
                    <td class="text-center">
                            <button value="on" type="submit" name="form-3-DELETE" class="btn btn-danger btn-sm">
                            <span class="glyphicon glyphicon-trash"></span> Excluir</button>
                            <input id="id_form-3-id" name="form-3-id" type="hidden" value="9">
                    </td>
                </tr>

            </tbody>

    </table>
</div>    
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<script>
    function atualizarDinamico(object){
    		
        var indice = object.closest("tr").rowIndex - 1;
        var quantidade = $('#id_form-' + indice + '-quantidade').val();
        var preco = $('#id_form-' + indice + '-preco').val();

        console.log(quantidade);
        console.log(preco);
        console.log(object);

        console.log(parseFloat(quantidade) * parseFloat(preco));

        document.getElementById('total-'+ indice).innerHTML = parseFloat(quantidade) * parseFloat(preco); 
    }
</script>

Second example.

  • Jessika, thank you very much for your suggestion. I just got a question, my ids are generated automatically, how could I reference these inputs? Sure your solution works, just need to know how to reference the inputs that are created dynamically. Thanks.

  • Tries to call the update functionTotal in input: <input type="text" oninput="atualizarTotal(idPreco,idQnt,idTotal)">, Modifying the function upTotal to be dynamic would work for any id you pass by parameter. I edited the answer with 1 example

  • Jessika, the oninput is definitely the solution. I managed to take the price, quantity and calculate the total, I just need to update the <td> that is after the price for the total. Using Parent would be the best solution? Thanks for the help. I’ve included the current code already with the updates in my question.

  • Take a look at the second example =)!! I used the closest to catch the tr father of input and so I was able to get the index to generate the dynamic ids. I put the total inside a span and put the id following their same idea of the ids. By taking the id of the total I changed the value within the spanwith the .html.

  • I’ll test it now, I’ll get back to you. Thank you.

  • Perfect!!! Excellent solution. Thank you so much for your help.

Show 1 more comment

Browser other questions tagged

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