Hide " Add to cart " button for 1 day after ordering a product, for that product which user has ordered - wordpress

I have added a new custom field in checkout page named " Date of event ", It's working fine. But i want one thing to be done which is " When user order single/multiple products then hide "Add to cart" button and show unavailable message instead of button for that selected date of event. " Like if user selected date " 7/2/2019 " in " Date of event field " during checkout, then after he ordered that product, hide " Add to cart " button and show unavailable message instead of button for " 7/2/2019 " date of event. I don't know how to do this.
Which hooks and actions will do this. I have googled it a lot, but didn't get any answer.
Please help me.
Custom field Code:
add_action('woocommerce_after_checkout_billing_form', 'date_of_event_field');
function date_of_event_field($checkout){
echo '<div id="date_of_event_field" class="margin-top-20">';
woocommerce_form_field( 'date_of_event', array(
'type' => 'date',
'class' => array('my-field-class form-row-wide'),
'label' => __('Date Of Event'),
'required' => true,
), $checkout->get_value( 'date_of_event' ));
echo '</div>';
}
Code to hide Add to cart button and show message instead of button:
function make_product_unavailable( $_product, $order ) {
if( $order->id == $_product ){
remove_action( 'woocommerce_after_shop_loop_item', 'woocommerce_template_loop_add_to_cart');
remove_action( 'woocommerce_single_product_summary', 'woocommerce_template_single_add_to_cart');
}
}
It's a try from my side, because i don't know how to do to this and i don't know which filter/action hook will be used for this.
Please help me.

Source : https://wisdmlabs.com/blog/the-right-way-to-hide-add-to-cart-button-in-woocommerce/
Check if a customer has purchased a specific products in WooCommerce
Note : The below code is not tested but it will work if some part is modified as per your requirement..
add_filter( 'woocommerce_is_purchasable', 'hidecart',10,1);
function hidecart(){
$found = has_bought_items();
if(!empty($found["order_date"])){
$current_date = date("d/m/Y");
if($found["order_date"] == $current_date && $found["product_id"] == get_the_ID()){
return false;
}
}
}
function has_bought_items()
{
$bought = false;
$order_date = '';
//get product id if single or for shop page u will have to retrieve in some other way
$product_id = get_the_ID();
// Get all customer orders
$customer_orders = get_posts( array(
'numberposts' => -1,
'meta_key' => '_customer_user',
'meta_value' => get_current_user_id(),
'post_type' => 'shop_order', // WC orders post type
'post_status' => 'wc-completed' // Only orders with status "completed"
) );
foreach ( $customer_orders as $customer_order ) {
// Updated compatibility with WooCommerce 3+
$order_id = method_exists( $order, 'get_id' ) ? $order->get_id() : $order->id;
$order = wc_get_order( $customer_order );
// Iterating through each current customer products bought in the order
foreach ($order->get_items() as $item) {
// WC 3+ compatibility
if ( version_compare( WC_VERSION, '3.0', '<' ) )
$order_product_id = $item['product_id'];
else
$order_product_id = $item->get_product_id();
// Your condition related to your 2 specific products Ids
if ( $product_id == $product_id) ) {
$bought = true;
$order_date = $order->order_date;
// you can fetch your event date stored as order meta
$arr = array("product_id"=>$product_id,"order_date"=>$order_date,"bought"=>$bought);
return $arr;
}
}
}
$arr = array("product_id"=>"","order_date"=>$order_date,"bought"=>$bought);
return $order_date;
}

Related

WooCommerce apply coupon depends of cart line item quantity

After long looking, I was not able to find any proper code how would be possible to apply coupon for a cart line items. Lets say customer added some product quantity of 10, my selected coupon should be applied for that product. If he adds another product with quantity more than 10, again same coupon should to be applied for that product.
Any assistance here?
I was able to find something similar but this only works for specific products id, any assistance how to update this code to go through each cart products ,check their quantities and apply coupon for products which quantity is 10 or more?
Reference for similar code but only for specific products:
Conditionally apply coupons automatically for specific Product IDs and quantities
Image example:
tried to create a custom solution for my question below. And did it in some way, not sure if this is proper and good option, but it at least work for me as exactly I need. This creates a separate coupon for every product in a shop (if newly product added it creates an unique coupon for it as well). Coupons is applied automatically per cart line item, if product quantity is 10 or more in a cart. It gives a 10% discount for that product. Code as per below, maybe for someone will be useful as I couldn't find any plugins or codes to work like this anywhere...
$args = array(
'posts_per_page' => -1,
'orderby' => 'title',
'order' => 'asc',
'post_type' => 'shop_coupon',
'post_status' => 'publish',
);
$all_coupons = get_posts( $args );
// Loop through the available coupons
foreach ( $all_coupons as $coupon ) {
// Get the name for each coupon and add to the previously created array
$coupon_name = $coupon->post_title;
}
foreach ($all_coupons as $coupon) {
$coupons_array[] = $coupon->post_title;
}
$all_ids = get_posts( array(
'post_type' => 'product',
'numberposts' => -1,
'post_status' => 'publish',
'fields' => 'ids',
) );
foreach ( $all_ids as $id ) {
$product_id_array[] = $id;
}
// Get values from arr2 and arr1 unique
$output = array_merge(array_diff($coupons_array, $product_id_array), array_diff($product_id_array, $coupons_array));
function coupon_exists($coupon_code) {
global $wpdb;
$sql = $wpdb->prepare( "SELECT post_name FROM $wpdb->posts WHERE post_type = 'shop_coupon' AND post_name = '%s'", $coupon_code );
$coupon_codes = $wpdb->get_results($sql);
if (count($coupon_codes)> 0) {
return true;
}
else {
return false;
}
}
foreach ($output as $o) {
if (is_numeric($o)) {
if (!coupon_exists($o)) {
generate_coupon($o);
}
}
}
function generate_coupon($coupon_code){
$coupon = new WC_Coupon();
$coupon->set_code($coupon_code);
//the coupon discount type can be 'fixed_cart', 'percent' or 'fixed_product', defaults to 'fixed_cart'
$coupon->set_discount_type('percent_product');
//the discount amount, defaults to zero
$coupon->set_amount(10);
$coupon->set_individual_use(false);
$coupon->set_product_ids(array($coupon_code));
//save the coupon
$coupon->save();
return $coupon_code;
}
add_action( 'woocommerce_before_cart', 'conditional_auto_add_coupons' );
function conditional_auto_add_coupons() {
$all_ids = get_posts( array(
'post_type' => 'product',
'numberposts' => -1,
'post_status' => 'publish',
'fields' => 'ids',
) );
if ( !WC()->cart->is_empty() ){
// First cart loop: Counting number of subactegory items in cart
foreach ( $all_ids as $id ){
foreach ( WC()->cart->get_cart() as $cart_item ){
if( $id == $cart_item['data']->id ){
if( 10 <= $cart_item['quantity'] ){
WC()->cart->add_discount( $id );
//wc_add_notice( __( 'Discount of <strong>10%</strong> for quantity.', 'theme_domain' ), 'success' );
}else{
WC()->cart->remove_coupon( $id );
//wc_add_notice( __( 'Discount of <strong>10%</strong> due to low quantity removed.', 'theme_domain' ), 'success' );}
}
}
}
}
}
}

Allow current user to navigate only his own posts in wordpress

I am using a custom plugin to add previous and next links in the "admin edit post" page. This so that the author can easily skip from his own posts (previous to next) without having to leave that page in the backend.
I am however struggling with how I need to get there.
Is the below adjustable to make it display only the current editing user ?
function change_apn_post_status( $post_statuses, $post_type ) {
// Add a post status.
// Note: by default these are already in the $post_statuses array: 'draft', 'future', 'pending', 'private', 'publish'
$post_statuses[] = 'trash';
// Remove post status(es).
$post_statuses_to_remove = array( 'draft' ); // Customize here.
if ( 'page' === $post_type ) {
$post_statuses_to_remove[] = 'pending';
}
foreach ( $post_statuses_to_remove as $remove ) {
if ( false !== $index = array_search( $remove, $post_statuses ) ) {
unset( $post_statuses[ $index ] );
}
}
return array_values( $post_statuses );
}
add_filter( 'c2c_admin_post_navigation_post_statuses', 'change_apn_post_status', 10, 2 );'
I thought this was a good starting point but alas I can't get it to work
global $current_user;
wp_get_current_user();
$author_query = array(
'posts_per_page' => '-1',
'author' => $current_user->ID
);

How to Populate a Drop-down field in WP

I have a gravity form form on my WP site and I recently changed a free text field into a drop down field.
The website is a store which hold several categories of goods and I want my drop-down to show the user all the possible categories he can choose from.
Please assist in how to "pull" the categories into the drop-down list.
Thanks in advance.
You can do using some filters of gravity form, code is following
// Here 1 is form id
add_filter( 'gform_pre_render_1', 'populate_category' );
add_filter( 'gform_pre_validation_1', 'populate_category' );
add_filter( 'gform_pre_submission_filter_1', 'populate_category' );
add_filter( 'gform_admin_pre_render_1', 'populate_category' );
function populate_category( $form ) {
foreach ( $form['fields'] as &$field ) {
if ( $field->type != 'select' || strpos( $field->cssClass, 'populate-category' ) === false ) {
continue;
}
// Get category list
$categories = get_categories( array(
'orderby' => 'name',
'order' => 'ASC'
) );
$choices = array();
foreach( $categories as $category ) {
$choices[] = array( 'text' => $category->name, 'value' => $category->name );
}
$field->placeholder = 'Select a Category';
$field->choices = $choices;
}
return $form;
}
This is working perfectly its tested code.

Update user meta after woocommerce checkout form process

I am using woocommerce with Wordpress and have added some custom fields to the checkout:
add_action('woocommerce_after_order_notes', 'my_custom_checkout_field');
function my_custom_checkout_field( $checkout ) {
$extra_fields = array('job_title', 'company', 'telephone', 'occupation');
foreach($extra_fields as $key => $value) {
woocommerce_form_field($value, array(
'type' => 'text',
'class' => array('my-field-class form-row-wide'),
'label' => __($label),
'value' => '',
), $checkout->get_value( $value ));
}
}
Now currently, these appear in the checkout fine, not sure if using woocommerce_after_order_notes is right in this case. I have also added some custom fields to the user meta that correspond to the fields added to the checkout - which all display in the user profile page:
function add_contact_methods( $contactmethods ) {
$contactmethods['job_title'] = 'Job Title';
$contactmethods['company'] = 'Company Name';
$contactmethods['telephone'] = 'Telephone';
$contactmethods['occupation'] = 'Occupation';
$contactmethods['refer'] = 'How you heard about us?';
return $contactmethods;
}
add_filter('user_contactmethods','add_contact_methods',10,1);
As you can imagine, if I update any of these field in any profile page, it works fine but what I cant seem to do is update the user meta when a new user makes a purchase, it does not update the user meta for these fields in the database.
I understand alot of how this works, and understand that I must hook into a Woocommerce process to add the fields into the process. So I have added this code into my functions too:
add_action('woocommerce_checkout_update_user_meta', 'my_custom_checkout_field_update_user_meta');
function my_custom_checkout_field_update_user_meta( $user_id ) {
global $extra_fields;
foreach($extra_fields as $key => $value) {
if ($_POST[$value]) update_user_meta( $user_id, $value, esc_attr($_POST[$value]));
}
}
Now the twist is, this works if a user who is already signed in as a member, makes a repurchase and goes through the checkout - the reason this works is because $user_id already exists, but when a new user is checking out, they do not yet exist as a user, hence the function cannot update the user meta of NIL where $user_id does not exist.
My question is, how do I hook into the checkout process, presumably AFTER the user has been created, so I that I can get the $user_id returned, and execute this function to update the user meta.
class-wc-checkout.php line 639 creates the new user with $this->customer_id = wp_insert_user( apply_filters( 'woocommerce_new_customer_data', $new_customer_data ) ); The new customer data is an array listed just above that line.
Following that, you can access the user id with line 649's action do_action( 'woocommerce_created_customer', $this->customer_id );
It is unlikey, in your case, you will need to use the filter, but simply add the action 'woocommerce_created_customer', pull in the id, and add the meta.
When customer is not logged in checkout page should be acceptable field customer want to create a new account.Below sample code change in checkout page when customer order a new item and update user meta data.
function user_extra_meta_fields(){
return array(
'job_title' => __( 'Job Title', 'yourtext_domain'),
'company' => __( 'Company Name', 'yourtext_domain'),
'telephone' => __( 'Telephone', 'yourtext_domain'),
'occupation' => __( 'Occupation', 'yourtext_domain'),
'refer' => __( 'How you heard about us?', 'yourtext_domain'),
);
}
function add_contact_methods( $contactmethods ) {
$contactmethods = array_merge( $contactmethods, user_extra_meta_fields());
return $contactmethods;
}
add_filter('user_contactmethods','add_contact_methods',10,1);
add_action('woocommerce_after_order_notes', 'my_custom_checkout_field');
function my_custom_checkout_field( $checkout ) {
foreach( user_extra_meta_fields() as $name => $label) {
$value = '';
if( is_user_logged_in() )
$value = get_user_meta( get_current_user_id(), $name, true );
woocommerce_form_field( $name, array(
'type' => 'text',
'class' => array('my-field-class form-row-wide'),
'label' => $label,
), $value );
}
}
add_action( 'woocommerce_checkout_process', 'user_fields_woocommerce_checkout_process' );
function user_fields_woocommerce_checkout_process(){
if( is_user_logged_in() )
add_action('woocommerce_checkout_update_user_meta', 'my_custom_checkout_field_update_user_meta' );
else
add_action( 'woocommerce_created_customer', 'my_custom_checkout_field_update_user_meta' );
}
function my_custom_checkout_field_update_user_meta( $user_id ) {
foreach( array_keys( user_extra_meta_fields() ) as $meta_name ){
if( isset( $_POST[$meta_name] ) ){
$meta_value = $_POST[$meta_name] ? esc_attr($_POST[$meta_name]) : '';
update_user_meta( $user_id, $meta_name, $meta_value );
}
}
}
// if want to validate field
add_action( 'woocommerce_after_checkout_validation', 'user_fields_woocommerce_after_checkout_validation' );
function user_fields_woocommerce_after_checkout_validation( $posted ){
$validate = true;
if( ! is_user_logged_in() && empty( $posted['createaccount'] ) )
$validate = false;
if( $validate == false )
return;
$meta_data = user_extra_meta_fields();
foreach( array_keys( $meta_data ) as $meta_name ){
if( empty($_POST[$meta_name]) )
wc_add_notice( sprintf( __(' <strong>%s</strong> is required.', 'yourtext_domain'), $meta_data[$meta_name] ), 'error' );
}
}

Woocommerce product search not checking "product_tag"?

It appears as tho the search functionality for WooCommerce products does not check "product_tag" taxonomy terms, nor SKU field? I added the SKUs as product tags to their respective products, but it still returns nothing when I search for the SKU.... How do I make the search functionality check product_tag terms? I have tried many many many things from adding tax_query to pre_get_post filter, to a whole new WP_Query loop, it just fails to search product_tags for some reason....so what is the point in a Product Tag???
I've tried the code from woo and others to search SKU with no results. However, the plugin search-everything, download from repository, does the job.
I got the solution to search the products by SKU code.
It is too simple just paste the following code in function.php and then you can see the changes in search results.
function search_by_id_only( $search, &$query_vars ) {
global $wpdb, $pagenow;
if ( 'edit.php' == $pagenow || empty($search) ) {
return $search;
}
$args = array(
'posts_per_page' => -1,
'post_type' => 'product',
'meta_query' => array(
array(
'key' => '_sku',
'value' => $query_vars->query['s'],
'compare' => 'LIKE'
)
)
);
$posts = get_posts( $args );
if ( empty( $posts ) ) return $search;
$get_post_ids = array();
foreach($posts as $post){
$get_post_ids[] = $post->ID;
}
if ( sizeof( $get_post_ids ) > 0 ) {
$search = str_replace( 'AND (((', "AND ((({$wpdb->posts}.ID IN (" . implode( ',', $get_post_ids ) . ")) OR (", $search);
}
return $search;
}
add_filter( 'posts_search', 'search_by_id_only', 999, 2 );

Resources