Jump to content

Additional Shipping Cost Per Item.... +2, +3, +4 items etc


MartyW

Recommended Posts

Hey everyone,

 

I get how the weight settings work i.e. for an order below X kg's the price is Y but the problem I am having is when a customer buys 2 bulky items the total weight stays below the threshold of 30kg (My couriers limit per parcel) but when the size of the parcel goes above the volumetric cm3 size per parcel I have to send 2 parcels.

 

This is a question on cm3 volume not weight kg. Can I set an additional cost per order should an order go beyond a certain size (volume cm3 wise) I can see that prestaShop allows you to enter the package size of each item. Is there a setting for additional volume?

 

I am sure the PrestaShop developers have thought about this topic and I have seen other similar posts that have been left unresolved am I just missing somthing in the back office?

 

To me and my BASIC programming skills the PrestaShop developers could implement this with a simple if, if else statement in the prestaShop programming i.e.

 

in the back office there would be a box similar to -

 

"Additional shipping cost (per quantity):"

 

but it would be called somthing like -

 

Additional shipping cost (per additional item): +2,+3, +4 etc

 

users would enter the additionalItemShippingCost in the back office "perAdditionalItem" box; and within the PrestaShop code an ifStatement like this would be implemented

 

 

//Adding additional items by volume setting up a +2 cost
int x = itemQuantity;
double y = additionalItemShippingCost;

//if the item count is equal to 2
if (x == 2){
// then increment default cost for y/additionalItemShippingCost
y+1;
}

//nested if statment
if (x == 3){
// then increment default cost for y/additionalItemShippingCost
y+2;
}
//+3, +4, +4 etc
//else if
else if (x <2){
//do nothing
}

 

or using boolean's i.e. itemQuatity = 2 (True) AdditionalItemCost+;

 

There are more efficient ways to program this (ArrayList for example) but the above is as far as my programming skills go

 

Best regards and thanks for any the help on this topic

 

Marty

Edited by MartyW (see edit history)
Link to comment
Share on other sites

I had similar problem, when my client wanted to have diffrent shipping price for diffrent order volume eg.:

1 to 3 items = 3 EUR

4 to 6 items = 4.5 EUR

etc.

 

Additional to diffrent price per items volume, I had to take in to consideration situations where user from other country order items and prices are a little bit diffrent.

 

At the end I wrote courier module, and had a lot of strange math inside. It basicly looked like this:


class mycarrier extends CarrierModule
{
public  $id_carrier;

private $_html = '';
private $_postErrors = array();
private $_moduleName = 'mycarrier';


/*
** Construct Method
**
*/

public function __construct()
{
$this->name = 'mycarrier';
$this->tab = 'shipping_logistics';
$this->version = '1.0';
$this->author = 'Skorupa';
$this->limited_countries = array();

parent::__construct ();

$this->displayName = $this->l('My Carrier');
$this->description = $this->l('Offer your customers, different delivery methods that you want');
}


/*
** Install / Uninstall Methods
**
*/

public function install()
{
$carrierConfig = array(
0 => array('name' => 'My Carrier Name',
'id_tax_rules_group' => 0,
'active' => true,
'deleted' => 0,
'shipping_handling' => false,
'range_behavior' => 0,
'delay' => array('fr' => 'Description 1', 'en' => 'Description 1', Language::getIsoById(Configuration::get('PS_LANG_DEFAULT')) => 'Description 1'),
'id_zone' => 1,
'is_module' => true,
'shipping_external' => true,
'external_module_name' => 'mycarrier',
'need_range' => true
),
);

$id_carrier1 = $this->installExternalCarrier($carrierConfig[0]);
Configuration::updateValue('MYCARRIER1_CARRIER_ID', (int)$id_carrier1);
if (!parent::install() ||
  !Configuration::updateValue('MYCARRIER1_OVERCOST', '') ||
  !$this->registerHook('updateCarrier'))
return false;
return true;
}

public function uninstall()
{
// Uninstall
if (!parent::uninstall() ||
  !Configuration::deleteByName('MYCARRIER1_OVERCOST') ||
  !$this->unregisterHook('updateCarrier'))
return false;

// Delete External Carrier
$Carrier1 = new Carrier((int)(Configuration::get('MYCARRIER1_CARRIER_ID')));

// If external carrier is default set other one as default
if (Configuration::get('PS_CARRIER_DEFAULT') == (int)($Carrier1->id))
{
global $cookie;
$carriersD = Carrier::getCarriers($cookie->id_lang, true, false, false, NULL, PS_CARRIERS_AND_CARRIER_MODULES_NEED_RANGE);
foreach($carriersD as $carrierD)
if ($carrierD['active'] AND !$carrierD['deleted'] AND ($carrierD['name'] != $this->_config['name']))
Configuration::updateValue('PS_CARRIER_DEFAULT', $carrierD['id_carrier']);
}

// Then delete Carrier
$Carrier1->deleted = 1;
if (!$Carrier1->update())
return false;

return true;
}

public static function installExternalCarrier($config)
{
$carrier = new Carrier();
$carrier->name = $config['name'];
$carrier->id_tax_rules_group = $config['id_tax_rules_group'];
$carrier->id_zone = $config['id_zone'];
$carrier->active = $config['active'];
$carrier->deleted = $config['deleted'];
$carrier->delay = $config['delay'];
$carrier->shipping_handling = $config['shipping_handling'];
$carrier->range_behavior = $config['range_behavior'];
$carrier->is_module = $config['is_module'];
$carrier->shipping_external = $config['shipping_external'];
$carrier->external_module_name = $config['external_module_name'];
$carrier->need_range = $config['need_range'];

$languages = Language::getLanguages(true);
foreach ($languages as $language)
{
if ($language['iso_code'] == 'fr')
$carrier->delay[(int)$language['id_lang']] = $config['delay'][$language['iso_code']];
if ($language['iso_code'] == 'en')
$carrier->delay[(int)$language['id_lang']] = $config['delay'][$language['iso_code']];
if ($language['iso_code'] == Language::getIsoById(Configuration::get('PS_LANG_DEFAULT')))
$carrier->delay[(int)$language['id_lang']] = $config['delay'][$language['iso_code']];
}

if ($carrier->add())
{
$groups = Group::getGroups(true);
foreach ($groups as $group)
Db::getInstance()->autoExecute(_DB_PREFIX_.'carrier_group', array('id_carrier' => (int)($carrier->id), 'id_group' => (int)($group['id_group'])), 'INSERT');

$rangePrice = new RangePrice();
$rangePrice->id_carrier = $carrier->id;
$rangePrice->delimiter1 = '0';
$rangePrice->delimiter2 = '10000';
$rangePrice->add();

$rangeWeight = new RangeWeight();
$rangeWeight->id_carrier = $carrier->id;
$rangeWeight->delimiter1 = '0';
$rangeWeight->delimiter2 = '10000';
$rangeWeight->add();

$zones = Zone::getZones(true);
foreach ($zones as $zone)
{
Db::getInstance()->autoExecute(_DB_PREFIX_.'carrier_zone', array('id_carrier' => (int)($carrier->id), 'id_zone' => (int)($zone['id_zone'])), 'INSERT');
Db::getInstance()->autoExecuteWithNullValues(_DB_PREFIX_.'delivery', array('id_carrier' => (int)($carrier->id), 'id_range_price' => (int)($rangePrice->id), 'id_range_weight' => NULL, 'id_zone' => (int)($zone['id_zone']), 'price' => '0'), 'INSERT');
Db::getInstance()->autoExecuteWithNullValues(_DB_PREFIX_.'delivery', array('id_carrier' => (int)($carrier->id), 'id_range_price' => NULL, 'id_range_weight' => (int)($rangeWeight->id), 'id_zone' => (int)($zone['id_zone']), 'price' => '0'), 'INSERT');
}

// Copy Logo
if (!copy(dirname(__FILE__).'/carrier.jpg', _PS_SHIP_IMG_DIR_.'/'.(int)$carrier->id.'.jpg'))
return false;

// Return ID Carrier
return (int)($carrier->id);
}

return false;
}

public function getOrderShippingCost($params, $shipping_cost)
{
$content = array();
$product_list = $params->getProducts();

$sum = 0;

// Here you add your additional price.

return $shipping_cost+(float)Tools::ps_round($sum, 2);
/*
// This example returns shipping cost with overcost set in the back-office, but you can call a webservice or calculate what you want before returning the final value to the Cart
if ($this->id_carrier == (int)(Configuration::get('MYCARRIER1_CARRIER_ID')) && Configuration::get('MYCARRIER1_OVERCOST') > 1)
return (float)(Configuration::get('MYCARRIER1_OVERCOST'))+1;
if ($this->id_carrier == (int)(Configuration::get('MYCARRIER2_CARRIER_ID')) && Configuration::get('MYCARRIER2_OVERCOST') > 1)
return (float)(Configuration::get('MYCARRIER2_OVERCOST'))+2;
*/
// If the carrier is not known, you can return false, the carrier won't appear in the order process
return false;
}

public function getOrderShippingCostExternal($params)
{
// This example returns the overcost directly, but you can call a webservice or calculate what you want before returning the final value to the Cart

// If the carrier is not known, you can return false, the carrier won't appear in the order process
return false;
}
}

It was based on tutorial, but I can't find it anymore.

Edited by skorupa (see edit history)
  • Like 1
Link to comment
Share on other sites

Well its a start lol, my background is basic Java and some ASP.NET so ile have to dissect the code line by line or maybe even go as far as learning it :o. It definitely looks like a good start and more efficient than my if, if else

Edited by MartyW (see edit history)
Link to comment
Share on other sites

  • 2 weeks later...

Good afternoon Marty,

 

I hope you are doing well, thank you for your suggestion :)

 

At this time with PrestaShop you can:

  • Configure your shipping calcultations by price ranges
  • Configure your shipping calcultations by weight ranges
  • Configure your shipping calcultations per product quantity (e.g. $X * Y quantities of a specific product)
  • Set the W x L x D of a product (some carriers modules are using this to calculate the volume and determine the price)
  • Use a fixed cost or calculate the cost using UPS, USPS or FedEx API

At this time, we do not plan to introduce a new way of calculating the shipping cost (like the progressive discount offered by skorupa) however feel free to use skorupa's code or to override the Cart.php class. You can more specifically override the getOrderShippingCost() and getPackageShippingCost() methods to build your own custom calculation system ^_^

 

Regards,

  • Like 2
Link to comment
Share on other sites

Sure :)

 

Step 1: Log-in to your Back-office and go to "Catalog > Products"

Step 2: Edit the product for which you would like to set up an additional shipping cost

Step 3: Click on the "Shipping" sub-tab and fill the "Additional shipping cost (per quantity):" field

 

Here is a screenshot:

 

y9rq.png

 

Tip: Some merchants set all the shipping costs to $0 and are only using this feature to handle their shipping costs

  • Like 2
Link to comment
Share on other sites

Sure :)

 

Step 1: Log-in to your Back-office and go to "Catalog > Products"

Step 2: Edit the product for which you would like to set up an additional shipping cost

Step 3: Click on the "Shipping" sub-tab and fill the "Additional shipping cost (per quantity):" field

 

Here is a screenshot:

 

y9rq.png

 

Tip: Some merchants set all the shipping costs to $0 and are only using this feature to handle their shipping costs

 

Thanks for the tips. It will need a lot of work to set that for all products, though. :)

Link to comment
Share on other sites

  • 5 months later...

Sure :)

 

Step 1: Log-in to your Back-office and go to "Catalog > Products"

Step 2: Edit the product for which you would like to set up an additional shipping cost

Step 3: Click on the "Shipping" sub-tab and fill the "Additional shipping cost (per quantity):" field

 

It'd be awesome if it were possible to limit the additional cost per item to certain shipping methods. We have one shipping method where the user pays per item, but that's only cost effective up to so many items. so setting this value would affect the price of the other combined methods too.

  • Like 1
Link to comment
Share on other sites

  • 3 months later...

Hello,

 

I have a similar comment.

 

We are a serviced based company.  We arrange call out fees based on how far the customer is from our base.

 

The are products made for the different regions, have changed quantity to hours in translations.

 

Cannot add the call out fee as a combination, because the call out fee is charged only once, not every hour.

 

So I thought I can add the call out fee as a handling fee, but the handling fee is per item not per order.

 

Does anyone know how I could change the handling fee to inlcude the call out fee for that particular are which the products have been made for

 

Or is there another way to do this?

 

Does anyone know a good way to do a call out fee based on the customers location for a service based businesses website on prestashop? thank you

 

 

Thank you,

Andrea

Link to comment
Share on other sites

  • 5 weeks later...

@swifter how granular is call out fee, is it based on the coutry you call to?

 

Hi thank you for taking the time to answer @skorupa in the end I went for one of the paid modules which fixed it all up for me perfectly.

Link to comment
Share on other sites

  • 3 months later...

I used localized shipping and it is working.

 

The call out fee is because we are a serviced based industry covinging many locations within the state.  Our trucks might visit a customer 2 hours drive away to commence the job (removalist) of which there are varying call out fees ranging from 0 through to $129 and up to $189.  The call out fee is based upon postcode ranges.

 

Thanks,
Andrea.

Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
×
×
  • Create New...