2017-08-22 14:17:58 +00:00
|
|
|
<?php
|
|
|
|
/**
|
|
|
|
* Cart fees API.
|
|
|
|
*
|
2017-08-22 15:31:45 +00:00
|
|
|
* Developers can add fees to the cart via WC()->cart->fees_api() which will reference this class.
|
2017-08-22 14:17:58 +00:00
|
|
|
*
|
2017-08-22 15:31:45 +00:00
|
|
|
* We suggest using the action woocommerce_cart_calculate_fees hook for adding fees.
|
2017-08-22 14:17:58 +00:00
|
|
|
*
|
|
|
|
* @package WooCommerce/Classes
|
2018-03-16 17:43:53 +00:00
|
|
|
* @version 3.2.0
|
2017-08-22 14:17:58 +00:00
|
|
|
*/
|
|
|
|
|
2018-03-16 17:43:53 +00:00
|
|
|
defined( 'ABSPATH' ) || exit;
|
2017-08-22 14:17:58 +00:00
|
|
|
|
|
|
|
/**
|
|
|
|
* WC_Cart_Fees class.
|
|
|
|
*
|
|
|
|
* @since 3.2.0
|
|
|
|
*/
|
|
|
|
final class WC_Cart_Fees {
|
|
|
|
|
|
|
|
/**
|
|
|
|
* An array of fee objects.
|
|
|
|
*
|
|
|
|
* @var object[]
|
|
|
|
*/
|
|
|
|
private $fees = array();
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Reference to cart object.
|
|
|
|
*
|
|
|
|
* @since 3.2.0
|
2017-09-27 16:12:45 +00:00
|
|
|
* @var WC_Cart
|
2017-08-22 14:17:58 +00:00
|
|
|
*/
|
|
|
|
private $cart;
|
|
|
|
|
|
|
|
/**
|
|
|
|
* New fees are made out of these props.
|
|
|
|
*
|
|
|
|
* @var array
|
|
|
|
*/
|
|
|
|
private $default_fee_props = array(
|
|
|
|
'id' => '',
|
|
|
|
'name' => '',
|
|
|
|
'tax_class' => '',
|
|
|
|
'taxable' => false,
|
|
|
|
'amount' => 0,
|
2017-08-23 11:15:06 +00:00
|
|
|
'total' => 0,
|
2017-08-22 14:17:58 +00:00
|
|
|
);
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Constructor. Reference to the cart.
|
|
|
|
*
|
|
|
|
* @since 3.2.0
|
2017-09-27 16:12:45 +00:00
|
|
|
* @throws Exception If missing WC_Cart object.
|
2017-09-27 16:16:33 +00:00
|
|
|
* @param WC_Cart $cart Cart object.
|
2017-08-22 14:17:58 +00:00
|
|
|
*/
|
2017-09-27 16:12:45 +00:00
|
|
|
public function __construct( &$cart ) {
|
|
|
|
if ( ! is_a( $cart, 'WC_Cart' ) ) {
|
|
|
|
throw new Exception( 'A valid WC_Cart object is required' );
|
|
|
|
}
|
|
|
|
|
2017-08-22 14:17:58 +00:00
|
|
|
$this->cart = $cart;
|
2017-11-03 19:49:45 +00:00
|
|
|
}
|
|
|
|
|
2017-12-08 16:24:04 +00:00
|
|
|
/**
|
|
|
|
* Register methods for this object on the appropriate WordPress hooks.
|
|
|
|
*/
|
|
|
|
public function init() {}
|
|
|
|
|
2017-08-22 14:17:58 +00:00
|
|
|
/**
|
|
|
|
* Add a fee. Fee IDs must be unique.
|
|
|
|
*
|
|
|
|
* @since 3.2.0
|
|
|
|
* @param array $args Array of fee properties.
|
|
|
|
* @return object Either a fee object if added, or a WP_Error if it failed.
|
|
|
|
*/
|
|
|
|
public function add_fee( $args = array() ) {
|
|
|
|
$fee_props = (object) wp_parse_args( $args, $this->default_fee_props );
|
2017-08-22 15:12:37 +00:00
|
|
|
$fee_props->name = $fee_props->name ? $fee_props->name : __( 'Fee', 'woocommerce' );
|
2018-03-16 17:43:53 +00:00
|
|
|
$fee_props->tax_class = in_array( $fee_props->tax_class, array_merge( WC_Tax::get_tax_classes(), WC_Tax::get_tax_class_slugs() ), true ) ? $fee_props->tax_class : '';
|
2017-08-22 14:17:58 +00:00
|
|
|
$fee_props->taxable = wc_string_to_bool( $fee_props->taxable );
|
|
|
|
$fee_props->amount = wc_format_decimal( $fee_props->amount );
|
|
|
|
|
|
|
|
if ( empty( $fee_props->id ) ) {
|
|
|
|
$fee_props->id = $this->generate_id( $fee_props );
|
|
|
|
}
|
|
|
|
|
|
|
|
if ( array_key_exists( $fee_props->id, $this->fees ) ) {
|
|
|
|
return new WP_Error( 'fee_exists', __( 'Fee has already been added.', 'woocommerce' ) );
|
|
|
|
}
|
|
|
|
|
2018-03-16 17:43:53 +00:00
|
|
|
$this->fees[ $fee_props->id ] = $fee_props;
|
|
|
|
|
|
|
|
return $this->fees[ $fee_props->id ];
|
2017-08-22 14:17:58 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Get fees.
|
|
|
|
*
|
|
|
|
* @return array
|
|
|
|
*/
|
|
|
|
public function get_fees() {
|
2017-08-22 15:12:37 +00:00
|
|
|
uasort( $this->fees, array( $this, 'sort_fees_callback' ) );
|
|
|
|
|
|
|
|
return $this->fees;
|
2017-08-22 14:17:58 +00:00
|
|
|
}
|
|
|
|
|
2017-08-22 15:20:23 +00:00
|
|
|
/**
|
|
|
|
* Set fees.
|
|
|
|
*
|
|
|
|
* @param object[] $raw_fees Array of fees.
|
|
|
|
*/
|
|
|
|
public function set_fees( $raw_fees = array() ) {
|
|
|
|
$this->fees = array();
|
|
|
|
|
|
|
|
foreach ( $raw_fees as $raw_fee ) {
|
|
|
|
$this->add_fee( $raw_fee );
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2017-08-22 14:17:58 +00:00
|
|
|
/**
|
|
|
|
* Remove all fees.
|
|
|
|
*
|
|
|
|
* @since 3.2.0
|
|
|
|
*/
|
|
|
|
public function remove_all_fees() {
|
|
|
|
$this->set_fees();
|
|
|
|
}
|
|
|
|
|
2017-08-22 15:12:37 +00:00
|
|
|
/**
|
|
|
|
* Sort fees by amount.
|
|
|
|
*
|
2019-07-31 21:31:49 +00:00
|
|
|
* @param stdClass $a Fee object.
|
|
|
|
* @param stdClass $b Fee object.
|
2017-08-22 15:12:37 +00:00
|
|
|
* @return int
|
|
|
|
*/
|
|
|
|
protected function sort_fees_callback( $a, $b ) {
|
2019-07-31 21:31:49 +00:00
|
|
|
/**
|
|
|
|
* Filter sort fees callback.
|
|
|
|
*
|
|
|
|
* @since 3.8.0
|
|
|
|
* @param int Sort order, -1 or 1.
|
|
|
|
* @param stdClass $a Fee object.
|
|
|
|
* @param stdClass $b Fee object.
|
|
|
|
*/
|
|
|
|
return apply_filters( 'woocommerce_sort_fees_callback', $a->amount > $b->amount ? -1 : 1, $a, $b );
|
2017-08-22 15:12:37 +00:00
|
|
|
}
|
|
|
|
|
2017-08-22 14:17:58 +00:00
|
|
|
/**
|
|
|
|
* Generate a unique ID for the fee being added.
|
|
|
|
*
|
2017-08-22 15:20:23 +00:00
|
|
|
* @param string $fee Fee object.
|
2017-08-22 14:17:58 +00:00
|
|
|
* @return string fee key.
|
|
|
|
*/
|
|
|
|
private function generate_id( $fee ) {
|
2017-08-22 15:12:37 +00:00
|
|
|
return sanitize_title( $fee->name );
|
2017-08-22 14:17:58 +00:00
|
|
|
}
|
|
|
|
}
|