1

I am trying to add a VAT field to the Customer Billing Address, while this works on the Checkout page with the following code:

// Company Name Required
add_filter('woocommerce_checkout_fields','custom_override_checkout_fields');
function custom_override_checkout_fields($fields){
    $fields['billing']['billing_company']['required'] = true;
    $fields['billing']['billing_vat'] = array(
    'label'       => __('VAT Number','woocommerce'),
    'placeholder' => _x('Enter VAT Number','placeholder','woocommerce'),
    'required'    => true,
    'class'       => array('form-row-wide'),
    'clear'       => true
    );
    return $fields;
}
//Display field value on the order edit page
add_action('woocommerce_admin_order_data_after_shipping_address','my_custom_checkout_field_display_admin_order_meta',10,1);
function my_custom_checkout_field_display_admin_order_meta($order){
    echo '<p><strong>'.__('VAT Number').':</strong> ' . get_post_meta($order->id,'_billing_vat',true) . '</p>';
}
//Order the fields
add_filter("woocommerce_checkout_fields","order_fields");
function order_fields($fields){
    $order = array(
        "billing_first_name",
        "billing_last_name",
        "billing_company",
        "billing_vat",
        "billing_country",
        "billing_city",
        "billing_postcode",
        "billing_state",
        "billing_address_1",
        "billing_address_2",
        "billing_email",
        "billing_phone",
    );
foreach($order as $field){$ordered_fields[$field] = $fields["billing"][$field];}
$fields["billing"] = $ordered_fields;
return $fields;
}

I also require it to be set on the Customer Billing Address in the account options. As I require to link this to the registration page as I'd like the users to register with all their credentials including the VAT number they own for a B2B Webstore.

Does anyone know or could anyone point me in the right direction how I would perform this task of not only showing those billing fields of the VAT number on the checkout page but also on the users profile page, as well as how to add all these fields on the registration page?

Thanks in advance for any assistance for this case!

Rafaël De Jongh
  • 898
  • 2
  • 14
  • 32

1 Answers1

3

Well, it's quite simple. Your code should be like this:

/* ---------------------- Registration page ----------------------- */

/* Add extra fields in registration form */
add_action( 'woocommerce_register_form_start', 'my_extra_register_fields' );
function my_extra_register_fields() {
?>
    <p class="woocommerce-FormRow woocommerce-FormRow--wide form-row form-row-wide">
        <label for="reg_billing_vat"><?php _e( 'Billing VAT', 'woocommerce' ); ?><span class="required">*</span></label>
        <input type="text" class="input-text" name="billing_vat" id="reg_billing_vat" value="<?php if ( ! empty( $_POST['billing_vat'] ) ) esc_attr_e( $_POST['billing_vat'] ); ?>">
    </p>
    <div class="clearfix"></div>
<?php
}

/* registration form fields Validation */
add_action( 'woocommerce_register_post', 'my_validate_extra_register_fields', 10, 3 );
function my_validate_extra_register_fields( $username, $email, $validation_errors ) {

    if ( isset( $_POST['billing_vat'] ) && empty( $_POST['billing_vat'] ) ) {
        $validation_errors->add( 'billing_vat_error', __( 'VAT number is required!', 'woocommerce' ) );
    }   

    return $validation_errors;
}

/* Below code save extra fields when new user register */
add_action( 'woocommerce_created_customer', 'my_save_extra_register_fields' ); 
function my_save_extra_register_fields( $customer_id ) {

    if ( isset( $_POST['billing_vat'] ) ) {     

        // VAT field which is used in WooCommerce
        update_user_meta( $customer_id, 'billing_vat', sanitize_text_field( $_POST['billing_first_name'] ) );
    }

}


/* ---------------------- Account page ----------------------- */

/* Show custom fields on Account details page */
add_action( 'woocommerce_edit_account_form', 'my_woocommerce_edit_account_form' );
function my_woocommerce_edit_account_form() {
    $user_id = get_current_user_id();
    $user    = get_userdata( $user_id );

    if ( !$user ) return;

    $billing_vat = get_user_meta( $user_id, 'billing_vat', true );
?>
    <fieldset>
        <legend>Custom information</legend>

        <p class="woocommerce-FormRow woocommerce-FormRow--wide form-row form-row-wide">
            <label for="billing_vat">Billing VAT</label>
            <input type="text" name="billing_vat" id="billing_vat" value="<?php echo esc_attr( $billing_vat ); ?>" class="input-text" />
        </p>
        <div class="clearfix"></div>

    </fieldset>
   <?php
}

/* Below code save extra fields when account details page form submitted */
add_action( 'woocommerce_save_account_details', 'my_woocommerce_save_account_details' );
function my_woocommerce_save_account_details( $user_id ) {

    if ( isset( $_POST['billing_vat'] ) ) {
        update_user_meta( $user_id, 'billing_vat', sanitize_text_field( $_POST['billing_vat'] ) );
    }

}

You can add more custom fields as per your need.

And yes you can add custom fields under my-account/edit-address/billing/ by using woocommerce_billing_fields filter hook.

So the code for this, should be like below:

/* Add field under my account billing  */
add_filter( 'woocommerce_billing_fields', 'my_woocommerce_billing_fields' );
function my_woocommerce_billing_fields( $fields ) {

    $user_id = get_current_user_id();
    $user    = get_userdata( $user_id );

    if ( !$user ) return;

    $fields['billing_vat'] = array(
        'type'      => 'text',
        'label'     => __('VAT', 'woocommerce'),
        'placeholder'   => _x('VAT Number', 'placeholder', 'woocommerce'),
        'required'  => true,
        'class'     => array('form-row'),
        'clear'     => true,
        'default'   => get_user_meta( $user_id, 'billing_vat', true ) // assing default value if any
    );

    return $fields;
}

/* Format custom field to show on my account billing  */
add_filter( 'woocommerce_my_account_my_address_formatted_address', 'custom_my_account_my_address_formatted_address', 10, 3 );
function custom_my_account_my_address_formatted_address( $fields, $customer_id, $name ) {

    $fields['vat']  = get_user_meta( $customer_id, $name . '_vat', true );

    return $fields;
}

/* Replace the key for custom field to show on my account billing  */
add_filter( 'woocommerce_formatted_address_replacements', 'custom_formatted_address_replacements', 10, 2 );
function custom_formatted_address_replacements( $address, $args ) {
    $address['{vat}'] = '';

    if ( ! empty( $args['vat'] ) ) {
        $address['{vat}'] = __( 'VAT Number', 'woocommerce' ) . ': ' . $args['vat'];
    }

    return $address;
}   
add_filter( 'woocommerce_localisation_address_formats', 'custom_localisation_address_format' );
function custom_localisation_address_format( $formats ) {

    foreach($formats as $key => $value) :
        $formats[$key] .= "\n\n{vat}";
    endforeach;

    return $formats;
}
Ritz Cool
  • 396
  • 1
  • 6
  • Awesome thanks for the assistance! I The additional field for the registration seems to be working and I now also understand how to add more to to the registration page. However I do notice that the VAT field appears under the Account Details however I would like to have it under the Billing Address (my-account/edit-address/billing/). I might be able to change this by addressing the hook differently or so? Like "woocommerce_after_edit_account_address_form" I do wonder if there's a way to order the elements. Either way I do thank you for the effort you've put into helping me already! – Rafaël De Jongh Apr 11 '17 at 15:44
  • You're welcome! I have edited my answer to add custom fields under Billing Address (my-account/edit-address/billing/). Let me know if it works for you. :-) – Ritz Cool Apr 12 '17 at 08:43
  • Marked as accepted answer and thanks a million man! Great support! Keep up the fantastic work I'd say, it's great to see there are still awesome people on this world! – Rafaël De Jongh Apr 12 '17 at 14:50
  • Most welcome @RafaëlDeJongh ! Glad to know it helped you :) – Ritz Cool Apr 12 '17 at 17:14
  • An additional question to this main question, is it also possible to add this information to the backend from Wordpress as in on the "wp-admin/user-edit.php" page's Customers Billing Address? Like everything works perfectly now on the frontend, but as the intention of having moderation on the users with a valid VAT number is the main concept, having the option to also see the customer's VAT number in the backstage would of course be required. I'm replying to this as this has a relation to my main question, but I do thank you in general already for everything you've done! – Rafaël De Jongh Apr 13 '17 at 23:34
  • I know it has something to do with "woocommerce_customer_meta_fields" but I'm currently unsuccessful at altering the array. – Rafaël De Jongh Apr 14 '17 at 00:43
  • 1
    Aha seems the structure was just a bit different than what I expected it to be, looking further in the actual source code I managed to make it work with the following: add_filter('woocommerce_customer_meta_fields','add_custom_meta_field'); function add_custom_meta_field($fields){ $fieldData = array('label' => 'VAT Number'); $fields['billing']['fields']['billing_vat'] = $fieldData; return $fields; } Either way thanks for your help, sometimes explaining it to yourself and writing it down in a help thread actually makes you solve these things! – Rafaël De Jongh Apr 14 '17 at 00:52