Hola
Hola

Reputation: 83

jQuery: price doesn't update - it doesn't subtract correctly (using switch statement)

I have searched this site for something similar to my question, but haven't found anything. If there's something I missed, please send me the link and I'll look at it.

I have a form where the total price of a fictitious booking is to be calculated from hotel price + (amount of people * excursion price). The more excursions the end-user chooses, the more the price increases. So far, so good. My problem is when, say, I check more than 1 excursion and then change my mind and uncheck one of them (or 2), that the subtraction part of my jQuery code doesn't work, for some reason. It will keep adding the price, except when there is one excursion left - if you uncheck it then it will subtract.

The form is a PHP form where all the hotel and excursion options are retrieved from a database.

To do this (the restrictions of the assignment don't allow me to use plugins for this particular part), I'm using the following code:

$(function() { 
//other code snippets

$(".excursions").change(function() {
    var x = $("#price").val();
    var excursions = $(this).val();
    var q = $("#quantity").val();
    var quantity = parseInt(q);
    var isChecked = $('.excursions').is(':checked');

    if (isChecked) {
        switch (excursions) {
            case 'Extreme sports day (or 2 days) in Jarabacoa':
                var y = parseFloat(x) + (parseFloat(1.000) * quantity);
                $("#price").val(y.toFixed(3) + " DKK");
                break;
            case 'Hiking/Mountaineering at the Caribbean Alps':
                var y = parseFloat(x) + (parseFloat(1.500) * quantity);
                $("#price").val(y.toFixed(3) + " DKK");
                break;
            case 'Whale Watching and Visit to Salto El Limón':
                var y = parseFloat(x) + (parseFloat(1.150) * quantity);
                $("#price").val(y.toFixed(3) + " DKK");
                break;
            case 'Carnival at La Vega and La Vega City Tour':
                var y = parseFloat(x) + (parseFloat(1.000) * quantity);
                $("#price").val(y.toFixed(3) + " DKK");
                break;
            case '"Restaurant Crawl": Taste The Dominican Republic':
                var y = parseFloat(x) + (parseFloat(1.500) * quantity);
                $("#price").val(y.toFixed(3) + " DKK");
                break;
            case 'Gastronomy routes: coffee, chocolate, mango':
                var y = parseFloat(x) + (parseFloat(1.000) * quantity);
                $("#price").val(y.toFixed(3) + " DKK");
                break;
        } 
    } else {
        switch (excursions) {
            case 'Extreme sports day (or 2 days) in Jarabacoa':
                var y = parseFloat(x) - (parseFloat(1.000) * quantity);
                $("#price").val(y.toFixed(3) + " DKK");
                break;
            case 'Hiking/Mountaineering at the Caribbean Alps':
                var y = parseFloat(x) - (parseFloat(1.500) * quantity);
                $("#price").val(y.toFixed(3) + " DKK");
                break;
            case 'Whale Watching and Visit to Salto El Limón':
                var y = parseFloat(x) - (parseFloat(1.150) * quantity);
                $("#price").val(y.toFixed(3) + " DKK");
                break;
            case 'Carnival at La Vega and La Vega City Tour':
                var y = parseFloat(x) - (parseFloat(1.000) * quantity);
                $("#price").val(y.toFixed(3) + " DKK");
                break;
            case '"Restaurant Crawl": Taste The Dominican Republic':
                var y = parseFloat(x) - (parseFloat(1.500) * quantity);
                $("#price").val(y.toFixed(3) + " DKK");
                break;
            case 'Gastronomy routes: coffee, chocolate, mango':
                var y = parseFloat(x) - (parseFloat(1.000) * quantity);
                $("#price").val(y.toFixed(3) + " DKK");
                break;
        }
    }
    });
});

See it live: http://mari9b80.keaweb.dk/discoverejse/index.php?page=book

If I remove the second Switch statement, then the price won't decrease if I uncheck one excursion. What am I doing wrong?

Thanks in advance.

EDITED TO ADD: the solution to this question is in http://jsfiddle.net/xSSL4 - courtesy of Deryck. I accepted the answer because I couldn't accept his comment to it.

Upvotes: 1

Views: 179

Answers (1)

Deryck
Deryck

Reputation: 7668

NEW EDITS :)

Your problem is here:

var isChecked = $('.excursions').is(':checked');
if (isChecked) {
    ....

Your variable isChecked is not the BOOLEAN value you think it is. If even one of the excursions boxes is checked, this will return true. So even when you remove one or more, it still thinks true.

One thing you could do is add the number of :checked items together and on each input .change() verify the number against the last one to determine addition or subtraction.

New jQuery for you!

var checks = 0,
    price = 0;
$('.excursions').change(function () {
    var currentChecks = $('.excursions').filter(':checked').length;
    priceChange = parseFloat($(this).data('price'));
    if (checks < currentChecks) {
        price += priceChange;
        $('<span />').css('color', 'green').html('+$' + priceChange).appendTo('#total').fadeOut(1000, function () {
            $(this).remove();
        });
        checks = currentChecks;
        $('#price').html('$' + price);
    } else {
        price -= priceChange;
        $('<span />').css('color', 'red').html('-$' + priceChange).appendTo('#total').fadeOut(1000, function () {
            $(this).remove();
        });
        checks = currentChecks;
        $('#price').html('$' + price);
    }
});

Sweet freakin live demo

I'm really glad I took another look at this now that it's been a couple days. Totally didn't realize I was getting the # of checked items from $(this) haha.

So to show my apologies, I added a little $$ add/subtract fade out feature for you too.

Hope this helps a little more than the last one :)

Upvotes: 2

Related Questions