Hello,
SHORT INTRODUCTION
I was never satisfied with the native behaviour of "delayed shipping" feature in PS 1.6 - it just doesn't work properly and I wanted to improve it. I have added ajax support and changed its behaviour a little bit. Previously I have modified the behaviour of AVAILABILITY column (which I also described here) in shopping-cart-product-line.tpl, so it shows (STOCK quantity) and (ON REQUEST quantity, which is in fact (CART - STOCK) quantity) now.
Now, we have a several cases regarding the "delayed shipping" feature, which we have to investigate:
1) All products in cart have no stock (stock quantity <= 0) in the cart -> delayed shipping not appearing (in native PS it was appearing which was wrong) = works OK -> https://streamable.com/guvfv
2) All products in cart have positive stock (stock quantity > 0) -> delayed shipping appears when the cart quantity exceeds stock quantity - works OK -> https://streamable.com/3v7kh
3) Products in cart have both positive stock (stock quantity > 0) and no stock (stock quantity <= 0). I'm deleting out_of_stock products form the cart - works OK -> https://streamable.com/r3ipf
4) Products in cart have both positive stock (stock quantity > 0) and no stock (stock quantity <= 0). I'm deleting in_stock products form the cart - DOES NOT WORK - "delayed shipping" block does not disappear - need some help here -> https://streamable.com/zeyff
Code modifications:
File: \classes\Cart.php (or you could an override) -> I have added 2 functions, which are counting in_stock nad out_of_stock products in the cart
public function countOOSProducts()
{
$product_out_of_stock = 0;
foreach ($this->getProducts() as $product) {
if ((int)$product['quantity_available'] <= 0
&& (!$ignore_virtual || !$product['is_virtual'])) {
$product_out_of_stock++;
}
}
return $product_out_of_stock;
}
public function countISProducts()
{
$product_in_stock = 0;
foreach ($this->getProducts() as $product) {
if ((int)$product['quantity_available'] > 0
&& (!$ignore_virtual || !$product['is_virtual'])) {
$product_in_stock++;
}
}
return $product_in_stock;
}
I have added new variables to summary array() to pass them into front files, so the new array() looks like this:
$summary = array(
'delivery' => $delivery,
'delivery_state' => State::getNameById($delivery->id_state),
'invoice' => $invoice,
'invoice_state' => State::getNameById($invoice->id_state),
'formattedAddresses' => $formatted_addresses,
'products' => array_values($products),
'gift_products' => $gift_products,
'discounts' => array_values($cart_rules),
'is_virtual_cart' => (int)$this->isVirtualCart(),
'product_in_stock' => $this->countISProducts();,
'product_out_of_stock' => $this->countOOSProducts();,
'total_discounts' => $total_discounts,
'total_discounts_tax_exc' => $total_discounts_tax_exc,
'total_wrapping' => $this->getOrderTotal(true, Cart::ONLY_WRAPPING),
'total_wrapping_tax_exc' => $this->getOrderTotal(false, Cart::ONLY_WRAPPING),
'total_shipping' => $total_shipping,
'total_shipping_tax_exc' => $total_shipping_tax_exc,
'total_products_wt' => $total_products_wt,
'total_products' => $total_products,
'total_price' => $base_total_tax_inc,
'total_tax' => $total_tax,
'total_price_without_tax' => $base_total_tax_exc,
'is_multi_address_delivery' => $this->isMultiAddressDelivery() || ((int)Tools::getValue('multi-shipping') == 1),
'free_ship' =>!$total_shipping && !count($this->getDeliveryAddressesWithoutCarriers(true, $errors)),
'carrier' => new Carrier($this->id_carrier, $id_lang),
);
File: \themes\your_theme\js\cart-summary.js -> I have modified function updateCartSummary(json) a little bit by adding following code:
// Definition of variables, which will store the quantity exceeding 'stock quantity' in shopping cart
886: var OosProducts = 0;
887: var OosProductsTotal = 0;
// Definition of the variable storing text, which is apearing while product is out_of_stock and ordering is allowed
921: var available_later = product_list[i].available_later;
// Display quantity exceeding stock quantity in shopping cart
991: OosProducts = parseInt(product_list[i].quantity) - parseInt(product_list[i].quantity_available);
992: if (OosProducts > 0) {
993: $('#outofstock_availability_' + key_for_blockcart).html(available_later + ' (' + quantity + ': ' + OosProducts + ')');
994: $('#outofstock_availability_' + key_for_blockcart).show();
995: //$('#outofstock_availability_' + key_for_blockcart).html('On request - avg. completion time: 60 work days (Quantity: ' + OosProducts + ')');
996: }
997: else {
998: $('#outofstock_availability_' + key_for_blockcart).hide();
999: }
1000 OosProductsTotal += (parseInt(product_list[i].quantity) - parseInt(product_list[i].quantity_available));
// 'delayed shipping' behaviour
1007: if (parseInt(product_list[i].quantity_available) > 0) {
1008: if ((OosProducts-OosProductsTotal > 0 || OosProducts > 0) && (OosProducts == OosProductsTotal) || (OosProducts-OosProductsTotal < 0) || OosProducts > 0 && (OosProducts !== OosProductsTotal)) {
1009: $('.allow_seperated_package').show();
1010: $('.allow_seperated_package').css({'color':'white', 'background-color':'orange', 'padding':'10px', 'display':'inline-block'});
1011: } else {
1012: $('.allow_seperated_package').hide();
1013: }
1011: }
File: \themes\your_theme\shopping-cart.tpl -> I have modified the "delayed shipping" code:
638: <p class="allow_seperated_package" {if ($show_option_allow_separate_package && {$product_in_stock} > 0)}style="background: orange; padding: 10px; display: inline-block;"{else}style="display: none;"{/if}> 639: <input type="checkbox" name="allow_seperated_package" id="allow_seperated_package" {if $cart->allow_seperated_package}checked="checked"{/if} autocomplete="off"/ > 640: <label for="allow_seperated_package" class="checkbox inline"> 641: {l s='Send available products first'} 642: </label> 643: </p>
There is also a need to force page refresh after product "add to cart" action in cart summary page (shopping-cart.tpl) to make it work properly, since PS 1.6 does not support ajax for this action on cart summary page.
Best regards,
Radoslaw