Welcome Guest, Not a member yet? Register   Sign In
Solution to cart_update with Ajax
#1

[eluser]PeterGreffen[/eluser]
I followed the (rather good) tutorial on nettuts how-to-build-a-shopping-cart-using-codeigniter-and-jquery and everything works fine. The codeigniter Cart class does exactly what it is supposed to do.

In the tutorial, an Ajax post is used to add a product to a cart, but for updating, it uses a redirect, so the page is entirely refreshed after a product update. I wanted only the shopping cart to be refreshed, so here's how I did that.

I made this modification in the application/controllers/cart.php function add_cart_item:

Code:
function add_cart_item(){
  if($this->cart_model->validate_add_cart_item() == TRUE){
     // Check if user has javascript enabled
     if($this->input->post('ajax') != '1'){
        // you can comment the next line, because we are no longer redirecting.
        // redirect('cart'); // If javascript is not enabled, reload the page with new data
     } else {
        echo 'true'; // If javascript is enabled, return true, so the cart gets updated
     }
  }
}

In my view file, I don't display the shopping cart table as suggested in the tutorial, but I include a view file showing the contents of the cart. It is this part (and only this part) that will be refreshed after the update of a product.
So this is how it looks in the view of an e.g. product details page:

Code:
<div id="cart_content">
  &lt;?= $this->view('shop/view-cart.php'); ?&gt;
</div>

And here is the shop/view-cart.php that is included:

Code:
<div id="update_cart">

&lt;!-- displays a success or failure message like 'cart updated' --&gt;
<div id='cart_message'></div>

&lt;form id="upcart"&gt;

    <table width="100%" cellpadding="0" cellspacing="0">
          
        &lt;?php
        $i = 1;
        
        foreach($this->cart->contents() as $items){
            echo form_hidden('rowid[]', $items['rowid']);
            echo "<tr ";
            if($i&1) { // do the zebra :o)
                echo ' class="alt"';
            }?&gt;
              ><td>
                  &lt;?php echo form_input(array('name' => 'qty[]', 'value' => $items['qty'], 'maxlength' => '3', 'size' => '5')); ?&gt;
              </td>

              <td>&lt;?php echo $items['name']; ?&gt;</td>

              <td>&euro;&lt;?php echo $this->cart->format_number($items['price']); ?&gt;</td>
              <td>&euro;&lt;?php echo $this->cart->format_number($items['subtotal']); ?&gt;</td>
          </tr>

          &lt;?php
        $i++;
        }
        ?&gt;

        <tr>
            <td></td>
            <td></td>
            <td>Total</td>
            <td>&euro;&lt;?php echo $this->cart->format_number($this->cart->total()); ?&gt;</td>
        </tr>

</table>

&lt;input type='submit' value='Update'&gt;

&lt;/form&gt;
</div>

And the add this two Ajax calls in the view-cart:

1. on submitting the first form (called #cartform), we first post to the function add_cart_item() and if that is succesfull, we imediatelly get the updated cart with cart/show_cart:

Code:
$("#cartform form").submit(function() {
        var id = $(this).find('input[name=product_id]').val();
        var qty = $(this).find('input[name=quantity]').val();
        
         $.post('&lt;?= base_url() ?&gt;' + "cart/add_cart_item", { real_id: &lt;?=$product->prod_id?&gt;, product_id: id, quantity: qty },
            function(data){
                if(data == 'true'){
                        $.get('&lt;?= base_url() ?&gt;' + "cart/show_cart", function(cart){ // Get the contents of the url cart/show_cart  
                        $("#cart_content").html(cart); // Replace the cart
                        $("#cart_message").text('Added!');
                        $("#cart_message").fadeOut(2000);
                        });
                } else {
                    alert("Error adding product!");
                }
            });
        return false;
    });

2. We do a similar thing for the update_cart(): first post to cart/update_cart, and then directly load the updated cart with cart/show_cart, to have the updated cart without refreshing:

Code:
$(function(){
        $("#upcart").submit(function(){
            
            dataString = $("#upcart").serialize();
            
            $.ajax({
                type: "POST",
                cache: false,
                url: '&lt;?= base_url() ?&gt;' + "cart/update_cart",
                data: dataString,
                cache: false,
                success: function(msg){
                    // reload the (updated) cart
                    $.get('&lt;?= base_url() ?&gt;' + "cart/show_cart", function(cart){ // Get the contents of the url cart/show_cart  
                    $("#cart_content").html(cart); // Replace the cart
                    $("#cart_message").text('Updated!');
                    $("#cart_message").fadeOut(2000);
                    });
                }
                
            });
            return false;            
        });
    });

note: both functions go in the document.ready function on top of the view-cart.php
Code:
$(document).ready(function() {
// here
});

The cart Controller functions (basically the same as in the original tutorial):

Code:
function add_cart_item(){
        if($this->cart_model->validate_add_cart_item() == TRUE){
            echo 'true';
        }
    }
    
    function show_cart(){
        $this->load->view('shop/view-cart');
    }
    
    function update_cart(){
        $this->cart_model->validate_update_cart();
    }

The functions validate_add_cart and validate_update_cart are also identical to the original tutorial.

I hope it can help someone out there...
(BTW, I'm a designer, not a coder, so forgive me if my coding is not perfect...)
P.




Theme © iAndrew 2016 - Forum software by © MyBB