Merge pull request #22540 from woocommerce/update/price-slider-improvements
Make the price filter widget tax aware redux
This commit is contained in:
commit
95c5d145bb
|
@ -33,6 +33,7 @@ jQuery( function( $ ) {
|
|||
|
||||
var min_price = $( '.price_slider_amount #min_price' ).data( 'min' ),
|
||||
max_price = $( '.price_slider_amount #max_price' ).data( 'max' ),
|
||||
step = $( '.price_slider_amount' ).data( 'step' ) || 1,
|
||||
current_min_price = $( '.price_slider_amount #min_price' ).val(),
|
||||
current_max_price = $( '.price_slider_amount #max_price' ).val();
|
||||
|
||||
|
@ -41,6 +42,7 @@ jQuery( function( $ ) {
|
|||
animate: true,
|
||||
min: min_price,
|
||||
max: max_price,
|
||||
step: step,
|
||||
values: [ current_min_price, current_max_price ],
|
||||
create: function() {
|
||||
|
||||
|
|
|
@ -681,7 +681,33 @@ class WC_Query {
|
|||
*/
|
||||
private function price_filter_meta_query() {
|
||||
if ( isset( $_GET['max_price'] ) || isset( $_GET['min_price'] ) ) { // WPCS: input var ok, CSRF ok.
|
||||
$meta_query = wc_get_min_max_price_meta_query( $_GET ); // WPCS: input var ok, CSRF ok.
|
||||
$current_min_price = isset( $_GET['min_price'] ) ? floatval( wp_unslash( $_GET['min_price'] ) ) : 0; // WPCS: input var ok, CSRF ok.
|
||||
$current_max_price = isset( $_GET['max_price'] ) ? floatval( wp_unslash( $_GET['max_price'] ) ) : 9999999999; // WPCS: input var ok, CSRF ok.
|
||||
|
||||
/**
|
||||
* Adjust if the store taxes are not displayed how they are stored.
|
||||
* Kicks in when prices excluding tax are displayed including tax.
|
||||
*/
|
||||
if ( wc_tax_enabled() && 'incl' === get_option( 'woocommerce_tax_display_shop' ) && ! wc_prices_include_tax() ) {
|
||||
$tax_class = apply_filters( 'woocommerce_price_filter_widget_tax_class', '' ); // Uses standard tax class.
|
||||
$tax_rates = WC_Tax::get_rates( $tax_class );
|
||||
|
||||
if ( $tax_rates ) {
|
||||
$current_min_price -= WC_Tax::get_tax_total( WC_Tax::calc_inclusive_tax( $current_min_price, $tax_rates ) );
|
||||
$current_max_price -= WC_Tax::get_tax_total( WC_Tax::calc_inclusive_tax( $current_max_price, $tax_rates ) );
|
||||
}
|
||||
}
|
||||
|
||||
$step = max( apply_filters( 'woocommerce_price_filter_widget_step', 10 ), 1 );
|
||||
$current_min_price = floor( $current_min_price / $step ) * $step;
|
||||
$current_max_price = ceil( $current_max_price / $step ) * $step;
|
||||
|
||||
$meta_query = wc_get_min_max_price_meta_query(
|
||||
array(
|
||||
'min_price' => $current_min_price,
|
||||
'max_price' => $current_max_price,
|
||||
)
|
||||
); // WPCS: input var ok, CSRF ok.
|
||||
$meta_query['price_filter'] = true;
|
||||
|
||||
return $meta_query;
|
||||
|
|
|
@ -786,36 +786,14 @@ function wc_get_product_visibility_options() {
|
|||
* @return array
|
||||
*/
|
||||
function wc_get_min_max_price_meta_query( $args ) {
|
||||
$min = isset( $args['min_price'] ) ? floatval( $args['min_price'] ) : 0;
|
||||
$max = isset( $args['max_price'] ) ? floatval( $args['max_price'] ) : 9999999999;
|
||||
|
||||
/**
|
||||
* Adjust if the store taxes are not displayed how they are stored.
|
||||
* Kicks in when prices excluding tax are displayed including tax.
|
||||
*/
|
||||
if ( wc_tax_enabled() && 'incl' === get_option( 'woocommerce_tax_display_shop' ) && ! wc_prices_include_tax() ) {
|
||||
$tax_classes = array_merge( array( '' ), WC_Tax::get_tax_classes() );
|
||||
$class_min = $min;
|
||||
$class_max = $max;
|
||||
|
||||
foreach ( $tax_classes as $tax_class ) {
|
||||
$tax_rates = WC_Tax::get_rates( $tax_class );
|
||||
|
||||
if ( $tax_rates ) {
|
||||
$class_min = $min + WC_Tax::get_tax_total( WC_Tax::calc_exclusive_tax( $min, $tax_rates ) );
|
||||
$class_max = $max - WC_Tax::get_tax_total( WC_Tax::calc_exclusive_tax( $max, $tax_rates ) );
|
||||
}
|
||||
}
|
||||
|
||||
$min = $class_min;
|
||||
$max = $class_max;
|
||||
}
|
||||
$current_min_price = isset( $args['min_price'] ) ? floatval( $args['min_price'] ) : 0;
|
||||
$current_max_price = isset( $args['max_price'] ) ? floatval( $args['max_price'] ) : PHP_INT_MAX;
|
||||
|
||||
return apply_filters(
|
||||
'woocommerce_get_min_max_price_meta_query',
|
||||
array(
|
||||
'key' => '_price',
|
||||
'value' => array( $min, $max ),
|
||||
'value' => array( $current_min_price, $current_max_price ),
|
||||
'compare' => 'BETWEEN',
|
||||
'type' => 'DECIMAL(10,' . wc_get_price_decimals() . ')',
|
||||
),
|
||||
|
@ -849,11 +827,14 @@ function wc_get_product_tax_class_options() {
|
|||
* @return array
|
||||
*/
|
||||
function wc_get_product_stock_status_options() {
|
||||
return apply_filters( 'woocommerce_product_stock_status_options', array(
|
||||
return apply_filters(
|
||||
'woocommerce_product_stock_status_options',
|
||||
array(
|
||||
'instock' => __( 'In stock', 'woocommerce' ),
|
||||
'outofstock' => __( 'Out of stock', 'woocommerce' ),
|
||||
'onbackorder' => __( 'On backorder', 'woocommerce' ),
|
||||
) );
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -68,23 +68,45 @@ class WC_Widget_Price_Filter extends WC_Widget {
|
|||
return;
|
||||
}
|
||||
|
||||
$min_price = isset( $_GET['min_price'] ) ? wc_clean( wp_unslash( $_GET['min_price'] ) ) : null; // WPCS: input var ok, CSRF ok.
|
||||
$max_price = isset( $_GET['max_price'] ) ? wc_clean( wp_unslash( $_GET['max_price'] ) ) : null; // WPCS: input var ok, CSRF ok.
|
||||
if ( ! wc()->query->get_main_query()->post_count && null === $min_price && null === $max_price ) {
|
||||
// If there are not posts and we're not filtering, hide the widget.
|
||||
if ( ! WC()->query->get_main_query()->post_count && ! isset( $_GET['min_price'] ) && ! isset( $_GET['max_price'] ) ) { // WPCS: input var ok, CSRF ok.
|
||||
return;
|
||||
}
|
||||
|
||||
wp_enqueue_script( 'wc-price-slider' );
|
||||
|
||||
// Round values to nearest 10 by default.
|
||||
$step = max( apply_filters( 'woocommerce_price_filter_widget_step', 10 ), 1 );
|
||||
|
||||
// Find min and max price in current result set.
|
||||
$prices = $this->get_filtered_price();
|
||||
$min = floor( $prices->min_price );
|
||||
$max = ceil( $prices->max_price );
|
||||
$min_price = $prices->min_price;
|
||||
$max_price = $prices->max_price;
|
||||
|
||||
if ( $min === $max ) {
|
||||
// Check to see if we should add taxes to the prices if store are excl tax but display incl.
|
||||
$tax_display_mode = get_option( 'woocommerce_tax_display_shop' );
|
||||
|
||||
if ( wc_tax_enabled() && ! wc_prices_include_tax() && 'incl' === $tax_display_mode ) {
|
||||
$tax_class = apply_filters( 'woocommerce_price_filter_widget_tax_class', '' ); // Uses standard tax class.
|
||||
$tax_rates = WC_Tax::get_rates( $tax_class );
|
||||
|
||||
if ( $tax_rates ) {
|
||||
$min_price += WC_Tax::get_tax_total( WC_Tax::calc_exclusive_tax( $min_price, $tax_rates ) );
|
||||
$max_price += WC_Tax::get_tax_total( WC_Tax::calc_exclusive_tax( $max_price, $tax_rates ) );
|
||||
}
|
||||
}
|
||||
|
||||
$min_price = apply_filters( 'woocommerce_price_filter_widget_min_amount', floor( $min_price / $step ) * $step );
|
||||
$max_price = apply_filters( 'woocommerce_price_filter_widget_max_amount', ceil( $max_price / $step ) * $step );
|
||||
|
||||
// If both min and max are equal, we don't need a slider.
|
||||
if ( $min_price === $max_price ) {
|
||||
return;
|
||||
}
|
||||
|
||||
$current_min_price = isset( $_GET['min_price'] ) ? floor( floatval( wp_unslash( $_GET['min_price'] ) ) / $step ) * $step : $min_price; // WPCS: input var ok, CSRF ok.
|
||||
$current_max_price = isset( $_GET['max_price'] ) ? ceil( floatval( wp_unslash( $_GET['max_price'] ) ) / $step ) * $step : $max_price; // WPCS: input var ok, CSRF ok.
|
||||
|
||||
$this->widget_start( $args, $instance );
|
||||
|
||||
if ( '' === get_option( 'permalink_structure' ) ) {
|
||||
|
@ -93,15 +115,12 @@ class WC_Widget_Price_Filter extends WC_Widget {
|
|||
$form_action = preg_replace( '%\/page/[0-9]+%', '', home_url( trailingslashit( $wp->request ) ) );
|
||||
}
|
||||
|
||||
$min_price = null !== $min_price ? $min_price : apply_filters( 'woocommerce_price_filter_widget_min_amount', $min );
|
||||
$max_price = null !== $max_price ? $max_price : apply_filters( 'woocommerce_price_filter_widget_max_amount', $max );
|
||||
|
||||
echo '<form method="get" action="' . esc_url( $form_action ) . '">
|
||||
<div class="price_slider_wrapper">
|
||||
<div class="price_slider" style="display:none;"></div>
|
||||
<div class="price_slider_amount">
|
||||
<input type="text" id="min_price" name="min_price" value="' . esc_attr( $min_price ) . '" data-min="' . esc_attr( apply_filters( 'woocommerce_price_filter_widget_min_amount', $min ) ) . '" placeholder="' . esc_attr__( 'Min price', 'woocommerce' ) . '" />
|
||||
<input type="text" id="max_price" name="max_price" value="' . esc_attr( $max_price ) . '" data-max="' . esc_attr( apply_filters( 'woocommerce_price_filter_widget_max_amount', $max ) ) . '" placeholder="' . esc_attr__( 'Max price', 'woocommerce' ) . '" />
|
||||
<div class="price_slider_amount" data-step="' . esc_attr( $step ) . '">
|
||||
<input type="text" id="min_price" name="min_price" value="' . esc_attr( $current_min_price ) . '" data-min="' . esc_attr( $min_price ) . '" placeholder="' . esc_attr__( 'Min price', 'woocommerce' ) . '" />
|
||||
<input type="text" id="max_price" name="max_price" value="' . esc_attr( $current_max_price ) . '" data-max="' . esc_attr( $max_price ) . '" placeholder="' . esc_attr__( 'Max price', 'woocommerce' ) . '" />
|
||||
<button type="submit" class="button">' . esc_html__( 'Filter', 'woocommerce' ) . '</button>
|
||||
<div class="price_label" style="display:none;">
|
||||
' . esc_html__( 'Price:', 'woocommerce' ) . ' <span class="from"></span> — <span class="to"></span>
|
||||
|
|
Loading…
Reference in New Issue