在后端产品页面中创建自定义隐藏字段,并在 WooCommerce 产品中使用值排序

Create a custom hidden field in backend product pages and use value in WooCommerce products sort by

我正在使用 WooCommerce 制作电子商务网站。在这个论坛的帮助下,我能够编写一些有用的代码片段。但是,我现在卡在了某个代码上。

我拼凑了各个部分的代码,但我无法让它工作。

我想做的 - 以编程方式为折扣百分比创建自定义隐藏字段,然后使用该字段允许按折扣排序。

但是元数据似乎没有保存在后台。

当我按折扣排序时,我得到的只是这个'No products were found matching your selection.',即使有一些产品在打折。

这是我的代码:

//add_action ('woocommerce_process_product_meta', 'mycode_product_save_discount');
add_action ('woocommerce_admin_process_product_object', 'mycode_product_save_discount');

function mycode_product_save_discount ($product)
{
    $product = wc_get_product ($product);
    $regular_price = (float) $product->get_regular_price();
    $sale_price = (float) $product->get_sale_price();

    if (!empty($sale_price))
    {
        $discount_percent = round (100 - ($sale_price / $regular_price * 100), 4);
        $discount_percent = $_POST['_discount_percent'][$product];
        //update_post_meta ($post_id, '_discount_percent', $discount_percent);
        $product->update_meta_data ('discount_percent', $discount_percent);
        $product->save();
    }
}

add_filter ('woocommerce_get_catalog_ordering_args', 'mycode_add_discount_to_ordering_args');
function mycode_add_discount_to_ordering_args ($args)
{
    $orderby_value = isset ($_GET['orderby']) ? wc_clean ($_GET['orderby']) : apply_filters ('woocommerce_default_catalog_orderby', get_option ('woocommerce_default_catalog_orderby'));
    
    if (!is_post_type_archive ('product') && !is_shop() && isset($args['orderby']))
    {
        $orderby_value = $sort_args['orderby'];
    }
    if ('discount' == $orderby_value)
    {
        $args['orderby'] = 'meta_value_num';
        $args['order'] = 'DESC';
        $args['meta_key'] = '_discount_percent';
    }
    return $args;
}

add_filter ('woocommerce_default_catalog_orderby_options', 'mycode_add_discount_to_orderby');
add_filter ('woocommerce_catalog_orderby', 'mycode_add_discount_to_orderby');
function mycode_add_discount_to_orderby ($sortby)
{
    $sortby['discount'] = 'Sort by discount';
    return $sortby;
}

我需要更改什么才能使其正常工作?

你很接近,但你的代码包含一些小错误。

这应该足够了:

/*** For debugging purposes, remove this action hook if everything works!! ***/
function action_woocommerce_product_options_general_product_data() {
    // Text field
    woocommerce_wp_text_input( array(
        'id'                 => '_discount_percent',
        'label'              => __( 'Discount percent', 'woocommerce' ),
        'placeholder'        => '',
        'description'        => __( 'For debugging purposes, remove this action hook if everything works', 'woocommerce' ),
        'desc_tip'           => true,
        'custom_attributes'  => array( 'readonly' => true ),
    ));
}
add_action( 'woocommerce_product_options_general_product_data', 'action_woocommerce_product_options_general_product_data', 10, 0 );

/*** From here on the code below is needed so that everything would work smoothly ***/
// Save value
function action_woocommerce_admin_process_product_object( $product ) {    
    // Getters
    $regular_price = (float) $product->get_regular_price();
    $sale_price = (float) $product->get_sale_price();
    
    // NOT empty
    if ( ! empty( $sale_price ) ) {
        // Calculate
        $discount_percent = round( 100 - ( $sale_price / $regular_price * 100 ), 4 );

        // Update
        $product->update_meta_data( '_discount_percent', $discount_percent );
    }
}
add_action( 'woocommerce_admin_process_product_object', 'action_woocommerce_admin_process_product_object', 10, 1 );

// Ordering products based on the selected values
function filter_woocommerce_get_catalog_ordering_args( $args, $orderby, $order ) {    
    switch( $orderby ) {
        case 'discount':
            $args['orderby']  = 'meta_value';
            $args['order']    = 'ASC';
            $args['meta_key'] = '_discount_percent';
            break;
    }

    return $args;
}
add_filter( 'woocommerce_get_catalog_ordering_args', 'filter_woocommerce_get_catalog_ordering_args', 10, 3 );

// Orderby setting
function filter_orderby( $orderby ) {
    $orderby['discount'] = __( 'Sort by discount', 'woocommerce' );
    return $orderby;
}
add_filter( 'woocommerce_default_catalog_orderby_options', 'filter_orderby', 10, 1 );
add_filter( 'woocommerce_catalog_orderby', 'filter_orderby', 10, 1 );

这里显示的是保存后的值。这实际上不是必需的,但可以用于调试目的。