Display Custom Order Filter In WooCommerce - wordpress

I am trying to display a custom admin order column in WooCommerce and I am having a hard time getting the code right here.
I have this code:
add_filter( 'woocommerce_admin_order_data_after_order_details', 'display_order_data_in_admin', 10, 1);
function display_order_data_in_admin( $output )
global $wp_query
$output .= wc_product_dropdown_categories( array(
'show_option_none' => 'Filter by Location',
'taxonomy => 'product_tag',
'name' => 'product_tag',
'selectd' => isset( $wp_query->query_vars['product_tag'] ) ? $wp_query->vars['procut_tag'] :
) );
return $output;
}
I am having a hard time displaying a column for filtering my orders by location that has been selected in checkout.

add_filter( 'manage_edit-shop_order_columns', 'wc_add_new_order_admin_list_column' );
function wc_add_new_order_admin_list_column( $columns ) {
$columns['billing_country'] = 'Country';
return $columns;
}
add_action( 'manage_shop_order_posts_custom_column', 'wc_add_new_order_admin_list_column_content' );
function wc_add_new_order_admin_list_column_content( $column ) {
global $post;
if ( 'billing_country' === $column ) {
$order = wc_get_order( $post->ID );
echo $order->get_billing_country();
}
}

Related

Woocommerce - add field to Check pay method

I'd like to add a field on Check Payment that allows the order processor to insert a check number...please help! Check payment orders will only be entered by staff, not the public.
Add Field Here
I've searched all over and I'm stumped.
As per my understanding of your question, I have created this snippet which will help you with your requirement.
// add a field on the check payment type
add_filter( 'woocommerce_gateway_description', 'custom_check_payment_field', 10, 2 );
function custom_check_payment_field( $description, $payment_id ) {
if ( is_user_logged_in() ) {
$user = wp_get_current_user();
$current_user_role = (array) $user->roles;
if ( 'cheque' === $payment_id && $current_user_role[0] == 'administrator') {
ob_start();
echo '<div class="cheque-field">';
woocommerce_form_field(
'customer_cheque_number',
array(
'type' => 'text',
'label' => __( 'Enter cheque number', 'woocommerce' ),
'class' => array( 'form-row-wide' ),
'required' => true,
),
''
);
echo '<div>';
$description .= ob_get_clean();
}
}
return $description;
}
// save check number in meta/database
add_action( 'woocommerce_checkout_create_order', 'save_customer_cheque_number_order_meta', 10, 2 );
function save_customer_cheque_number_order_meta( $order, $data ) {
if ( isset( $_POST['customer_cheque_number'] ) && ! empty( $_POST['customer_cheque_number'] ) ) {
$order->update_meta_data( '_customer_cheque_number', esc_attr( $_POST['customer_cheque_number'] ) );
}
}
// show check number on orders page (OPTONAL)
add_action( 'woocommerce_get_order_item_totals', 'display_customer_cheque_number_on_order_totals', 10, 3 );
function display_customer_cheque_number_on_order_totals( $total_rows, $order, $tax_display ) {
if ( $order->get_payment_method() === 'cheque' && $customer_cheque_number = $order->get_meta( '_customer_cheque_number' ) ) {
$sorted_total_rows = array();
foreach ( $total_rows as $key_row => $total_row ) {
$sorted_total_rows[ $key_row ] = $total_row;
if ( $key_row === 'payment_method' ) {
$sorted_total_rows['customer_cheque_number'] = array(
'label' => __( 'Cheque number', 'woocommerce' ),
'value' => esc_html( $customer_cheque_number ),
);
}
}
$total_rows = $sorted_total_rows;
}
return $total_rows;
}
// add meta box on orders on woocommerce backend
add_action( 'add_meta_boxes', 'add_meta_boxes_callback' );
if ( ! function_exists( 'add_meta_boxes_callback' ) ) {
function add_meta_boxes_callback() {
add_meta_box( 'shop_order_fields', __( 'Cheque number', 'woocommerce' ), 'orders_cheque_number_custom_meta', 'shop_order', 'side', 'core' );
}
}
// show meta field with entered check number
if ( ! function_exists( 'orders_cheque_number_custom_meta' ) ) {
function orders_cheque_number_custom_meta() {
global $post;
$check_number = get_post_meta( $post->ID, '_customer_cheque_number', true ) ? get_post_meta( $post->ID, '_customer_cheque_number', true ) : '';
?>
<input type="text" style="width:250px;margin-top:15px" readonly name="readonly_check_number" value="<?php echo $check_number; ?>"></p>
<?php
}
}

I would like to add country of origin to products in woocommerce

Hi I would like to add country of origin while adding products and then sort products based on country of origin
Can I achieve this?
Add these functions to your theme's 'functions.php'.
Display & Save the Custom Field in Admin
// display field in admin
add_action('woocommerce_product_options_general_product_data', 'woocommerce_product_country_field');
function woocommerce_product_country_field()
{
global $woocommerce, $post;
$countries_obj = new WC_Countries();
$options = $countries_obj->__get('countries');
echo '<div class="product_country_field">';
woocommerce_wp_select(
array(
'id' => '_country_origin',
'label' => __('Country of origin', 'woocommerce'),
'options' => $options,
'desc_tip' => 'true'
)
);
echo '</div>';
}
// save fields
add_action('woocommerce_process_product_meta', 'woocommerce_product_country_fields_save');
function woocommerce_product_country_fields_save($post_id)
{
$woocommerce_country_origin = $_POST['_country_origin'];
if (!empty($woocommerce_country_origin))
update_post_meta($post_id, '_country_origin', esc_attr($woocommerce_country_origin));
}
Sort by Custom Field in Front-End
// sort field
function custom_add_country_ordering_args( $sort_args ) {
$orderby_value = isset( $_GET['orderby'] ) ? wc_clean( $_GET['orderby'] ) : apply_filters( 'woocommerce_default_catalog_orderby', get_option( 'woocommerce_default_catalog_orderby' ) );
switch( $orderby_value ) {
case '_country_origin':
$sort_args['orderby'] = 'meta_value';
$sort_args['order'] = 'asc';
$sort_args['meta_key'] = '_country_origin';
break;
case '_country_origin-desc':
$sort_args['orderby'] = 'meta_value';
$sort_args['order'] = 'desc';
$sort_args['meta_key'] = '_country_origin';
break;
}
return $sort_args;
}
add_filter( 'woocommerce_get_catalog_ordering_args', 'custom_add_country_ordering_args' );
//change sort dropdown
function custom_add_country_orderby( $sortby ) {
//remove default sorting
unset($sortby["popularity"]);
unset($sortby["rating"]);
unset($sortby["date"]);
unset($sortby["price"]);
unset($sortby["price-desc"]);
$sortby['_country_origin'] = __( 'Sort by Country of origin', 'woocommerce' );
$sortby['_country_origin-desc'] = __( 'Sort by Country of origin descending', 'woocommerce' );
return $sortby;
}
add_filter( 'woocommerce_default_catalog_orderby_options', 'custom_add_country_orderby' );
add_filter( 'woocommerce_catalog_orderby', 'custom_add_country_orderby' );
Please note that the products which has 'Country of origin' will only be displayed while sorting.
Filter by Custom Field in Front-End
Add this if you want filter rather than sort.
//add custom filter
add_action( 'woocommerce_before_shop_loop', 'filter_loop_start' );
function filter_loop_start( $query ){
$countries_obj = new WC_Countries();
$options = $countries_obj->__get('countries');
?>
<form name="product_filter_form" class="woocommerce-filtering" method="get">
<select name="country_origin" class="filterby" onChange="document.product_filter_form.submit();">
<option value="">Filter by Country of origin</option>
<?php foreach ($options as $key => $value) { ?>
<option value="<?php echo $key; ?>"<?php if($_GET['country_origin']==$key) echo ' selected'; ?>><?php echo $value; ?></option>
<?php } ?>
</select>
<input name="paged" value="1" type="hidden">
</form>
<?php
}
//modify query for filter
add_filter( 'pre_get_posts', 'my_modify_main_query' );
function my_modify_main_query( $query ) {
if( ! isset( $_GET['country_origin'] ) ) return $query;
$meta_query_args = array(
'meta_query' => array(
array(
'key' => '_country_origin',
'value' => sanitize_text_field( $_GET['country_origin'] ),
'compare' => 'LIKE',
)
)
);
$query->set('meta_query', $meta_query_args);
return $query;
}

Updating A Post Title Using GET Method and $wpdb Class

I have a programming exercise and I wanted to check if what I have done so far is the best way to update a post title based on setting the query string. In my example below I create a link for updating the post and validate the origin with a nonce. I used the template_redirect action as it only fires once where as the wp and parse_query actions seemed to fire multiple times. The GET request can come from a form submit or link click but I've only attached the link example but the code should work for both situations.
function update_post_title() {
global $wpdb;
$post_id = get_query_var( 'post_id', 0 );
$post_title = get_query_var( 'post_title', '' );
$post_nonce = get_query_var( 'update_post_title_nonce', '' );
if( ! empty( $post_title ) AND $post_id > 0 ) {
if ( ! wp_verify_nonce( $post_nonce, 'update_post_title_action' ) ) {
wp_die( 'Security check failed' );
}
$post_title = sanitize_text_field( $post_title );
//$post_slug = sanitize_title_with_dashes( $post_title );
$post_id = intval( $post_id );
$rows_affected = $wpdb->update(
$wpdb->posts,
array( 'post_title' => $post_title ),
array( 'ID' => $post_id ),
array( '%s'),
array( '%d' )
);
}
}
function add_custom_query_vars( $public_query_vars ) {
$public_query_vars[] = 'post_id';
$public_query_vars[] = 'post_title';
$public_query_vars[] = 'update_post_title_nonce';
return $public_query_vars;
}
add_filter( 'query_vars', 'add_custom_query_vars' );
add_action( 'template_redirect', 'update_post_title' );
Sample link generate.
global $post;
<a href="<?php echo wp_nonce_url( add_query_arg( array(
'post_id' => 123,
'post_title' => 'The New Title', ),
site_url( $post->post_name ) ),
'update_post_title_action',
'update_post_title_nonce' );
?>">Click To Update</a>

Generate a dropdown with woocommerce order numbers to use in contact form 7

I've been looking everywhere, but I just can't find it.
I'd like to give users a way to ask for a refund, but in order to do this, they need to provide a mandatory order number. Ideally, this would be in a tab in the My Account page, but it could also be a simple shortcode dropped into a contact form 7 form.
I just can't find any solution, anywhere.
I did find one using Gravity Form, but I'd like to do it without a plugin.
Any help would be appreciated!
You need to modify and customize below code to load dynamic orders as your requirements:
Find here code snippet:
add_action( 'wpcf7_init', 'wpcf7_add_form_tag_orderno' );
function wpcf7_add_form_tag_orderno() {
wpcf7_add_form_tag( array( 'orderno', 'orderno*' ),
'wpcf7_orderno_form_tag_handler', array()
);
}
function wpcf7_orderno_form_tag_handler( $tag ) {
/* get all orders here*/
/*$customer_orders = wc_get_orders( array(
'limit' => -1,
'status' => array( 'wc-pending' )
));
// Iterating through each Order with pending status
foreach ( $customer_orders as $order ) {
$customer_orders = wc_get_orders( array(
'limit' => -1,
'status' => array( 'wc-pending' )
) );
// Iterating through each Order with pending status
foreach ( $customer_orders as $order ) {
// Going through each current customer order items
foreach($order->get_items() as $item_id => $item_values){
$product_id = $item_values['product_id']; // product ID
// Order Item meta data
$item_meta_data = wc_get_order_item_meta( $item_id );
// Some output
echo '<p>Line total for '.wc_get_order_item_meta( $item_id, '_line_total', true ).'</p><br>';
}
}*/
$options = '';
$options .= '<option>-- select order no ---</option>';
$options .= '<option value="1">Order #10001</option>';
$options .= '<option value="2">Order #10002</option>';
$options .= '<option value="3">Order #10003</option>';
/* use attributes */
$atts = array();
$atts['class'] = $tag->get_class_option( $class );
$atts['id'] = $tag->get_id_option();
$atts['tabindex'] = $tag->get_option( 'tabindex', 'int', true );
$atts['name'] = $tag->name;
$atts = wpcf7_format_atts( $atts );
$html = sprintf(
'<span class="wpcf7-form-control-wrap %1$s">
<select name="orderno">%2$s</select></span>',
sanitize_html_class( $tag->name ), $options);
return $html;
}
Add this shortcode in your contact form 7
[orderno orderno]
I hope it will be useful for you!
Here's what I came up with, thanks a lot for the cue!
add_action( 'wpcf7_init', 'wpcf7_add_form_tag_orderno' );
function wpcf7_add_form_tag_orderno() {
wpcf7_add_form_tag( array( 'orderno', 'orderno*' ),
'wpcf7_orderno_form_tag_handler', array()
);
}
function wpcf7_orderno_form_tag_handler( $tag ) {
$customer_orders = get_posts( apply_filters( 'woocommerce_my_account_my_orders_query',
array(
'numberposts' => $order_count,
'meta_key' => '_customer_user',
'meta_value' => get_current_user_id(),
'post_type' => wc_get_order_types( 'view-orders' ),
'post_status' => array_keys( wc_get_order_statuses() ),
) ) );
if ( $customer_orders ) {
$atts = array();
$atts['class'] = $tag->get_class_option( $class );
$atts['id'] = $tag->get_id_option();
$atts['tabindex'] = $tag->get_option( 'tabindex', 'int', true );
$atts['name'] = $tag->name;
$atts = wpcf7_format_atts( $atts );
echo '<select name="orderno">';
echo '<option>'.__( "Numéro de la commande", "sinope" ).'</option>';
foreach ( $customer_orders as $customer_order ) {
$order = wc_get_order( $customer_order );
$item_count = $order->get_item_count();
echo '
<option value="'.$order->get_order_number().'">
'.$order->get_order_number().'
</option>
';
}
echo '</select>';
}
}

Output error with get_post_meta in woocommerce

I am trying to add a custom metabox in woocommerce. It has been added perfectly. My ultimate goal is to call that custom field in a function and show it in the cart.php. So I coded :
For Custom field: [I would refer http://www.remicorson.com/mastering-woocommerce-products-custom-fields/] in this regard
add_action( 'woocommerce_product_options_general_product_data', 'woo_add_custom_general_fields' );
// Save Fields
add_action( 'woocommerce_process_product_meta', 'woo_add_custom_general_fields_save' );
function woo_add_custom_general_fields() {
global $woocommerce, $post;
echo '<div class="options_group">';
woocommerce_wp_text_input(
array(
'id' => 'number_field',
'label' => __( '<strong style="color:#239804">Your Free Products</strong>', 'woocommerce' ),
'placeholder' => '',
'description' => __( 'Please enter a number', 'woocommerce' ),
'type' => 'number',
'custom_attributes' => array(
'step' => 'any',
'min' => '0'
)
)
);
echo '</div>';
}//woo_add_custom_general_fields
function woo_add_custom_general_fields_save( $post_id ){
$woocommerce_number_field = $_POST['number_field'];
if( !empty( $woocommerce_number_field ) )
update_post_meta( $post_id, 'number_field', esc_attr( $woocommerce_number_field ) );
}//woo_add_custom_general_fields_save( $post_id )
It has perfectly fitted in the Product Admin Page. Now I am creating another function where I am creating a counter for cart.php
function free_products(){
global $woocommerce ,$product, $post;
foreach ( WC()->cart->get_cart() as $cart_item_key => $cart_item ) {
$free_number = get_post_meta( $post->ID, 'number_field', true );
$free_product = $cart_item['quantity'] * $free_number;
echo apply_filters( 'woocommerce_cart_item_quantity', $free_product, $cart_item_key );
}
}
In My cart.php when I add
<td class="product-quantity">
<?php
echo free_products();
?>
</td>
The output become zero in front end. Can anyone please help me what I am going wrong. Thanks in advance.
Try below code :
function free_products(){
global $woocommerce ,$product, $post;
foreach ( WC()->cart->get_cart() as $cart_item ) {
$my_var = $cart_item['product_id'];
$free_number = get_post_meta( $my_var, 'number_field', true );
$free_product = $cart_item['quantity'] * $free_number;
echo apply_filters( 'woocommerce_cart_item_quantity', $free_product);
}
}
Let me know if It is working for you or not.Its working for me.

Resources