使用PHP和数组进行实时计算

For a client i'm currently working on their new system. In this system they can create bookings/invoices and send them to their clients.

On 1 page my client is needed to fill in the price for each container in the qoutation. My client asked me to make a new table column below the container columns with the total prices for all containers. I want to do this real time, so when my client fills in the prices the total price changes.

The only problem I stumble on is this: I currently have PHP/MySQL function that collect all the containers from a certain quotation out of the database. With a while loop I create the needed html code for each of the containers. I made the input fields (where they fill in the prices) an array by naming the input fields like this:

<td>&euro; <input type="text" name="msg_container['.$i.'][ocean_freight]" value="'. $quote['ocean_freight'].'" style="width: 100px;" /></td>

The $i variable get's count up for each loop. It starts by 0 and ends when there are no containers left.

To make things a bit more detailed I have created a jsfiddle how the currently page looks like: https://jsfiddle.net/cwfmqbqv/

Now I'm not an expert in javascript so I'm stuck at this point. Long story short, how am I able to calculate all the values in the array in real time?

I've made a simple addition to your fiddle.

It's not complete as I only have time to make one for the Ocean Freight.

JSFiddle

$(document).ready(function() {
    $(".oceanIn").keyup(function() {
        var total = 0.0;
        $.each($(".oceanIn"), function(key, input) {
            if(input.value && !isNaN(input.value)) {
                total += parseFloat(input.value);
            }
        });
        $("#oceanTotal").html("Total: " + total);
     });
});

Also I added some class and id to some of your elements to make it work.

Note

For this one, I used keyup but feel free to use different events like change or blur, or whatever fits your needs.

You should have tried to learn the basics of Javascript before you went and looked for a client.

Also, I think you're confused between a column and a row.

This is similar to the first answer, but more complete, and the addition fires on keyup instead of on blur. It applies to all the columns without needing to create separate functions for each. Here's the fiddle.

Javascript

$(function(){
    $(".ocean-input, .bunker-input, .thc-input, .road-input").on("keyup", function()
    {
        var total = 0;

      $("." + $(this).attr('class')).each(function()
        {
            total += parseFloat($(this).val().replace('', 0).replace(',', '.'));
        });

            $("#" + $(this).data("total-id")).html(total.toString().replace('.', ','));

    });
});

HTML

<table width="100%" border="0" cellspacing="0" cellpadding="0" style="font-family:Arial, sans-serif; color:#000; font-size:12px;">

        <thead>
            <tr>
                <th width="50">Amount</th>
                <th>Type</th>
                <th>Weight (p/u)</th>
                <th>Shipping owned</th>
                <th>Ocean Freight</th>
                <th>Bunker Surcharge</th>
                <th>THC</th>
                <th>Road transport</th>
            </tr>
        </thead>

        <tbody>
            <tr>
            <td>1</td>
            <td>Container Type 1</td>
            <td>1000</td>
            <td>No</td>
            <td>&euro; <input type="text" class="ocean-input" data-total-id="ocean-total" name="msg_container[0][ocean_freight]" value="" style="width: 100px;"></td>
            <td>&euro; <input type="text" class="bunker-input" data-total-id="bunker-total" name="msg_container[0][bunker_surcharge]" value="" style="width: 100px;"></td>
            <td>&euro; <input type="text" class="thc-input" data-total-id="thc-total" name="msg_container[0][thc]" value="" style="width: 100px;"></td>
            <td>&euro; <input type="text" class="road-input" data-total-id="road-total" name="msg_container[0][road_transport]" value="" style="width: 100px;"></td>
        </tr><tr>
            <td>1</td>
            <td>Container Type 2</td>
            <td>2500</td>
            <td>No</td>
            <td>&euro; <input type="text" class="ocean-input" data-total-id="ocean-total" name="msg_container[1][ocean_freight]" value="" style="width: 100px;"></td>
            <td>&euro; <input type="text" class="bunker-input" data-total-id="bunker-total" name="msg_container[1][bunker_surcharge]" value="" style="width: 100px;"></td>
            <td>&euro; <input type="text" class="thc-input" data-total-id="thc-total" name="msg_container[1][thc]" value="" style="width: 100px;"></td>
            <td>&euro; <input type="text" class="road-input" data-total-id="road-total" name="msg_container[1][road_transport]" value="" style="width: 100px;"></td>
        </tr>       </tbody>

        <tfoot>
            <tr>
                <th width="50"></th>
                <th></th>
                <th></th>
                <th></th>
                <th>Total: &euro;<span id="ocean-total"></span></th>
                <th>Total: &euro;<span id="bunker-total"></span></th>
                <th>Total: &euro;<span id="thc-total"></span></th>
                <th>Total: &euro;<span id="road-total"></span></th>
            </tr>
        </tfoot>

    </table>

What you want is written in pure js in the following update to your jsfiddle: JSFiddle

The principal concept here was using the change event on inputs. Furthermore, I didn't change the naming of your inputs but consider better conventions.

In the total function, we get a type of columns we're dealing with (using custom attributes is better than just using input names. eg: column-type="thc") and calculate the total number of each related input. It uses Regular Expression (RegExp) in your case to find the right column out of input names. Mind that ~~ is just a simple hack for text to integer conversion in JavaScript.

Next we find all inputs and attach an event listener using addEventListener to each for the change event type. In this delegate, we find the appropriate input for total function and span IDs corresponding the column the input represents, again using RegExp but this time implicitly. Then change the corresponding span based on the total return value;