Skip Navigation

[Resolved] Booking form to buy a product

This support ticket is created 6 years, 2 months ago. There's a good chance that you are reading advice that it now obsolete.

This is the technical support forum for Toolset - a suite of plugins for developing WordPress sites without writing PHP.

Everyone can read this forum, but only Toolset clients can post in it. Toolset support works 6 days per week, 19 hours per day.

Sun Mon Tue Wed Thu Fri Sat
- 9:00 – 13:00 9:00 – 13:00 9:00 – 13:00 9:00 – 13:00 9:00 – 13:00 -
- 14:00 – 18:00 14:00 – 18:00 14:00 – 18:00 14:00 – 18:00 14:00 – 18:00 -

Supporter timezone: Asia/Hong_Kong (GMT+08:00)

This topic contains 16 replies, has 2 voices.

Last updated by Luo Yang 6 years, 1 month ago.

Assisted by: Luo Yang.

Author
Posts
#1111812

Hi,

WHAT I NEED
I need to set a CRED form to buy a product. Something like a booking form
I sell tours and prices are per person.

THE SITUATION
I have 2 custom fields displayed in the CRED form (Book-form):
- Number of adults =>

 [cred_field field='adult-number' value='' urlparam='' select_text='' class='form-control' output='bootstrap']

- Number of child =>

cred_field field='child-number' value='' urlparam='' select_text='' class='form-control' output='bootstrap']

In the backend I have 2 other fields used from me to add a price for a person and for a child in the backend:
- Price per person
- Price per child

I've also a function in the function.php file which override the woocommerce price with a calculation
Total = (Number of adults * Price per person) + (Number of child * Price per child)

This is the function:

function action_woocommerce_process_product_meta($post_id){ 
    global $woocommerce, $post;
	
		$price1 = $_POST['wpcf']['price-1'];
		$price2 = $_POST['wpcf']['price-2'];
		$adult-number= $_POST['wpcf']['adult-number'];
		$child-number= $_POST['wpcf']['child-number'];   
		$regular_price = ($price1 * $adult-number) + ($price2 * $child-number);		
		update_post_meta($post_id,'_regular_price',$regular_price);   
}
add_action('woocommerce_process_product_meta', 'action_woocommerce_process_product_meta', 30, 2 ); 

THE ISSUE
Ok, what I need now is to create a booking form to "build the price" and add the product to the cart.

Then I need to dispaly the booking form in the product page (built with Layouts) where a customer can select the number of person, the number of child and click on add to cart button. Of course, then run to the checkout page.

1) The problem is that using CRED I can't use the add to cart button but only the submit form button.

2) an other problem is that I don't have immediatly the preview of the price when I select number of adult and child. The price need to be saved before to be cahrged in the database.

How can I do?

Thanks a lot in advance for your help!

#1112140

Hello,

I don't think it is a good idea to change the product price each time user submit the form, it will take effect on other users who are going to buy the same product.

Here is my suggestion:
1) You can create two products with fixed price:
- adult
- child

2) When user submit the Toolset form, use action hook cred_commerce_form_action to trigger a PHP function, in this function setup the products and quantity according to user's input in "adult-number" and "child-number".

More help:
https://toolset.com/documentation/programmer-reference/cred-commerce-api/#cred_commerce_form_action
Action to be executed after CRED Commerce form has been submitted.

https://docs.woocommerce.com/wc-apidocs/source-class-WC_Cart.html#1023-1128
Add a product to the cart.

#1112145

Hi Luo,

Sorry, I didn't understand.

I have set tours as a products. I can't set an unique price becouse it chaghes in base of number of person and child.

Product Tours are not set from me but from external partners which use a CRED to "build" the product tour. When they fill the form, they set also the price for 1 person and for 1 child.

Untill this, every is ok.

My problem is the next step, when a customer want to book.

For this reason I need to build a booking form where the customer can chose number of adults and child. This allow to update the price and add the tour product to the cart with the right price.

You are right, is not a good idea to update the price in a definitve way but in a temporally way.
But how to do it?

So can you tel me to find a solution using Toolset?

#1112153

I have already provide a workaround with two fixed price products:
https://toolset.com/forums/topic/booking-form-to-buy-a-product/#post-1112140

If you still insist on using a dynamic price product, you can also use action hook cred_commerce_form_action to change the product price to what you want, see the document I mentioned above:
https://toolset.com/documentation/programmer-reference/cred-commerce-api/#cred_commerce_form_action

Since it is a custom codes problem, if you need more assistance, please provide a test site with the same problem, also point out the problem page URL and form URL, I need a live website to test and debug.

#1112195

Thanks for the details, the Toolset form you provided is not working at all, so I have to create another new and a fresh page to test the codes, here is the detail steps:
1) Create a form with similar settings:
hidden link

in section "Toolset Forms Commerce", enable option "Charge payment with this form", and select the specific product "Doggy Tour Chianti"

3) Add below codes into your theme file "functions.php":

add_action( 'cred_commerce_before_add_to_cart', 'my_hook', 10, 2 );
function my_hook( $form_id, $post_id ) {
	if ( $form_id == 24662 ) {
		$adult_number = $_POST['wpcf-adult-number'];
		$children_number = $_POST['wpcf-children-number'];
		$regular_price = 200 * $adult_number + 100 * $children_number; // here setup your custom price value
		update_post_meta($product_id = 24166,'_regular_price',$regular_price); 
	}
}

2) Create a page to test above form:
hidden link
after submit the form, go to the product post:
hidden link
You should be able to see the product price is changed.

#1112204

Ok Luo,

This is a good solution but not for my issue.

1) I need a form to applicate not only to one specific product. I need a form to applicate to all my products copying the form code in the layout will be automatically apply to all tour product. You have linked bookingform2 to one product not to all of them.

2) What a need is not to upadat the regular price of th product but the price of the singulat order (now Iunderstand sorry!). The regular price is the same (200 per persone and 100 per child), but with the calculation the order price should be changed not the product price. Infact if I go to the order details the price of bought is 0,00 €. Should be 600,00€ for 2 person and 2 children that I tested. Please check here => hidden link

#1112715

They are complete different problems from your original question:
https://toolset.com/forums/topic/booking-form-to-buy-a-product/#post-1111812

To avoid more misunderstandings, I assume we are talking about this case
In a single product post, there are two custom fields: "adult-price" + "children-price"

1) Display a Toolset form for creating woocommerce order post, with two fields "adult-number" + "children-number", after user submit the form,
2) After user submit the form, you are going to:
- put the current(dynamic) product into woocommerce cart
- change the woocomerce cart price to:
"adult-price" * "adult-number" + "children-price" * "children-number"

Can you confirm it?

If it is, there isn't such kind of built-in feature within Toolset form, and Toolset form can not be used to create the Woocommerce order post, it will conduct other unexpected result.

But there might be some other workarounds with custom codes, for example:
1) You can setup the Toolset form for creating another custom post type "my-order".
2) After user submit the form, use filter hook "cred_commerce_add_product_to_cart" to change the product in cart to what you want.
https://toolset.com/documentation/programmer-reference/cred-commerce-api/#cred_commerce_add_product_to_cart
3) use the woocommerce filter hook woocommerce_cart_item_price to change the cart price
hidden link

Please confirm them first, if you need assistance for setup the custom codes, I can setup a demo in your website.

#1112722

Hi, yes, this is my aim.
I confirm the assisitance for setup this code and I wait your demo
Thank you Luo

#1112838

I have done below modifications in your website:
1) Setup a custom post type "my-order"
hidden link

2) Setup a field group to post type "my-order"
hidden link
with two custom fields:
- adult-number
- children-number

3) I assume you are using:
- custom field "prezzo-1" stores "adult-price" value
- custom field "prezzo-2" stores "child-price" value

4) Setup the post form "bookform 2", in the post content, add a hidden field:
hidden link

[cred_generic_field type='hidden' field='product-id']
{
"default":"[wpv-post-id]"
}
[/cred_generic_field]

use it to pass the product post ID

5) in above post form, in section "Toolset Forms Commerce", enable option "Charge payment with this form"

6) Add below codes into your theme file "functions.php":

// Change the product ID
add_filter('cred_commerce_add_product_to_cart', function($product_id, $form_id, $post_id){
    if($form_id == 24662){
        if(isset($_POST['product-id'])){
            $product_id = $_POST['product-id'];
        }
    }
    return $product_id;
}, 20, 3);

// add URL parameter to checkout page
add_filter('cred_commerce_form_action', function($action, $form_id, $post_id, $form_data){
	$url = get_permalink( wc_get_page_id( 'checkout' ) );
	if($form_data['id']==24662){
		$url = add_query_arg( array(
			'target_post_id' => $post_id,
		), $url );
	}
    wp_redirect( $url);
    exit();
}, 999, 4);

// change the price in cart
add_action('woocommerce_before_calculate_totals', function(){
	if($form_id != 24662 && !isset($_GET['target_post_id']))return;
	global $woocommerce;
	
	$post_id = $_GET['target_post_id']; 
	$price = 0;
	foreach ( $woocommerce->cart->get_cart() as $key => $cart_item ) {
			
		$product_id = $cart_item['data']->get_id();
		$adult_price = get_post_meta($product_id, 'wpcf-prezzo-1', true);
		$adult_num = get_post_meta($post_id, 'wpcf-adult-number', true);
		$child_price = get_post_meta($product_id, 'wpcf-prezzo-2', true);
		$child_num = get_post_meta($post_id, 'wpcf-children-number', true);
			
		$price = $adult_price * $adult_num + $child_price * $child_num; 
		$cart_item['data']->set_price($price); 
	}
	
}, 999);

7) Put the post form into your layout, see the bottom of it, row 13
hidden link

Test it in front-end:
hidden link

After submit the form, you should be able to see the price is changed. and it is only an demo for your reference.

#1112878

Hi, I tried to book. I set 2 adult and 1 child, and booking for these.
When click on the button I was bring on the cart page but it show me that the cart is empty.

Maybe because I've not set any as regular price

If I set a regular price when click on the button I was bring on the checkout page but there is a problem with the price. When the page is charging the price is correct (from calcualtion of adult and child), but when the page finish to charge tre price is automatically updated to the regular price

#1112925

As I mentioned above it is only an demo, for show how to use the Toolset form API hooks
1) It is needed to setup the product regular price, or you it will redirect you to the empty cart page, this a limitation of Woocommerce

2) I have changed the PHP codes, use a PHP session to save the post ID:

// Change the product ID
add_filter('cred_commerce_add_product_to_cart', function($product_id, $form_id, $post_id){
    if($form_id == 24662){
		session_start();
        if(isset($_POST['product-id'])){
			$product_id = $_POST['product-id'];
			$_SESSION['target_post_id']   = $post_id;
        }
    }
    return $product_id;
}, 20, 3);

// change the price in cart
add_action('woocommerce_before_calculate_totals', function(){
	session_start();
	if($form_id != 24662 && !isset($_SESSION['target_post_id']))return;
	global $woocommerce;
	
	$post_id = $_SESSION['target_post_id']; 
	$price = 0;
	foreach ( $woocommerce->cart->get_cart() as $key => $cart_item ) {
			
		$product_id = $cart_item['data']->get_id();
		$adult_price = get_post_meta($product_id, 'wpcf-prezzo-1', true);
		$adult_num = get_post_meta($post_id, 'wpcf-adult-number', true);
		$child_price = get_post_meta($product_id, 'wpcf-prezzo-2', true);
		$child_num = get_post_meta($post_id, 'wpcf-children-number', true);
			
		$price = $adult_price * $adult_num + $child_price * $child_num; 
		$cart_item['data']->set_price($price); 
	}
	
}, 999);

Please test again, check if it is fixed.

#1114879

Hi Luo, sorry for late in my reply but I wrote immediatly, I don't know why my post is not saved in this discussion.

So, everything works, thank you very much.

The only 2 issue are:

1) the first issue is about where data is stored. Data as number of people and number of child, ecc ar very important. How is possible to save it in the woocommerce order meta? should be great to have the possibility to call this data in the order detail and in the order email which my partner received automaticcally by woocommerce. My partner don't have access to the backend and to my-order custom post, but only to the detail of woocommerce order. At the moment in this detail there is only the finla price, they cannot know how many adults, childs acc.

2) the second issue is the title of my-order that is a problem because in a booking form can confuse the customer. Is it possible to hide this field and assign an automatically title? And is also possilbe in your opinion to saved only temporary the post? Because what I need is the final order not this post type. after

#1114918

Q1) How is possible to save it in the woocommerce order meta?

There isn't such kind of feature too, it needs custom codes, after user complete the payment, the "order" post will be created by Woocommerce plugin, you can use action hook "cred_commerce_after_order_completed" to trigger another PHP function, use it to save the data as order meta.

If you need more assistance for it, please create new thread for the new questions, that will help other users to find the answers. You can assign the new ticket to me directly

Q2) the second issue is the title of my-order that is a problem because in a booking form can confuse the customer.

Yes, you just need to edit the Toolset form, remove the post title field:
[cred_field field="post_title" class="form-control" output="bootstrap"]

Then Toolset form will setup the post title automatically, for example:
CRED Auto Draft 837ec5754f503cfaaee0929fd48974e7

#1114939

Ok Luo, I open the new ticket immediatly, thanks!

Just another question on this thread .

When I fille the booking form if I don't fill all field required the page is recarched with the error message.
This is a little "bad" for th user. Is it possible to do something to exlude the recharge of the page but simple exit the error message?

#1114943

How can I asign the new ticket to you? When I open a newone it give me Shane as possibility not you

New threads created by Luo Yang and linked to this one are listed below:

https://toolset.com/forums/topic/how-is-possible-to-save-it-in-the-woocommerce-order-meta/