9

I'm following this tutorial on how to add an extra field to my variation products.

I just need to add an extra text field. The admin part works fine - the field is showing and saving/updating, however, the single product page doesn't - the field won't show.

So in my functions.php I've added:

add_action( 'woocommerce_product_after_variable_attributes', 'variation_settings_fields', 10, 3 );

add_action( 'woocommerce_save_product_variation', 'save_variation_settings_fields', 10, 2 );

function variation_settings_fields( $loop, $variation_data, $variation ) {
    woocommerce_wp_text_input( 
        array( 
            'id'          => '_text_field[' . $variation->ID . ']', 
            'label'       => __( 'Some label', 'woocommerce' ), 
            'placeholder' => '',
            'desc_tip'    => 'true',
            'description' => __( 'Some description.', 'woocommerce' ),
            'value'       => get_post_meta( $variation->ID, '_text_field', true )
        )
    );
}

function save_variation_settings_fields( $post_id ) {
    $text_field = $_POST['_text_field'][ $post_id ];
    if( ! empty( $text_field ) ) {
        update_post_meta( $post_id, '_text_field', esc_attr( $text_field );
    }
}

add_filter( 'woocommerce_available_variation', 'load_variation_settings_fields' );

function load_variation_settings_fields( $variations ) {

    $variations['text_field'] = get_post_meta( $variations[ 'variation_id' ], '_text_field', true );

    return $variations;
}

And in plugins/plugins/woocommerce/templates/single-product/add-to-cart/variation.php I've added (the theme doesn't have it's own variation.php):

<div class="woocommerce-variation-custom-text-field">
    {{{ data.variation.text_field }}}
</div>

How to display the custom field on the single product page?

Thanks

Update: If I inspect the single product page, the script is present:

<script type="text/template" id="tmpl-variation-template">
    <div class="woocommerce-variation-description">
        {{{ data.variation.variation_description }}}
    </div>

    <div class="woocommerce-variation-price">
        {{{ data.variation.price_html }}}
    </div>

   <div class="woocommerce-variation-custom-text-field">
        {{{ data.variation.text_field }}}
    </div>

    <div class="woocommerce-variation-availability">
        {{{ data.variation.availability_html }}}
    </div>
</script>

The theme is belise.

Update: I'm looking at the themes custom woocommerce functions.php (belise/inc/woocommerce/functions.php) file and the logic seems to be there.

/**
 * Shop page woocommerce-Price-amount amountption on product archives
 */
function belise_woocommerce_template_single_excerpt() {
    global $post;

    if ( ! $post->post_excerpt ) {
        return;
    }
    ?>
    <div class="woocommerce-Price-amount amountption" itemprop="woocommerce-Price-amount amountption">

        <!-- if I add <p>test</p> it is printed on the product page -->
        <!-- I would like for the custom field element to be printed here -->

        <?php echo apply_filters( 'woocommerce_short_woocommerce-Price-amount amountption', $post->post_excerpt ); ?>
    </div><?php
}

Answer - @ClemC first solution works, the field didn't show because of the browsers cache.

0

1 Answer 1

23
+50

For serious reference, see how WC itself adds the textarea variable_description to the variations here.

We notice multiple (potential) problems in your text field implementation.

  • The missing name...
  • The id string does not have a correct structure, it has the name structure instead...
  • The id or name are not same than in your template...

So taking as reference the WC variable_description textarea implementation, let's implement our text field this way:

add_action( 'woocommerce_product_after_variable_attributes', 'variation_settings_fields', 10, 3 );
add_action( 'woocommerce_save_product_variation', 'save_variation_settings_fields', 10, 2 );
add_filter( 'woocommerce_available_variation', 'load_variation_settings_fields' );

function variation_settings_fields( $loop, $variation_data, $variation ) {
    woocommerce_wp_text_input(
        array(
            'id'            => "my_text_field{$loop}",
            'name'          => "my_text_field[{$loop}]",
            'value'         => get_post_meta( $variation->ID, 'my_text_field', true ),
            'label'         => __( 'Some label', 'woocommerce' ),
            'desc_tip'      => true,
            'description'   => __( 'Some description.', 'woocommerce' ),
            'wrapper_class' => 'form-row form-row-full',
        )
    );
}

function save_variation_settings_fields( $variation_id, $loop ) {
    $text_field = $_POST['my_text_field'][ $loop ];

    if ( ! empty( $text_field ) ) {
        update_post_meta( $variation_id, 'my_text_field', esc_attr( $text_field ));
    }
}

function load_variation_settings_fields( $variation ) {     
    $variation['my_text_field'] = get_post_meta( $variation[ 'variation_id' ], 'my_text_field', true );

    return $variation;
}

Now, in the template that must have the following path:

yourtheme/woocommerce/single-product/add-to-‌​cart/variation.php

Add this:

<div class="random-class woocommerce-variation-custom-text-field">
    {{{ data.variation.my_text_field }}}
</div>

EDIT:

If you want to output your custom field the "classic" way:

<div class="woocommerce-variation-custom-text-field">
    <p><?php echo esc_html( get_post_meta( $post->ID, 'my_text_field', true ) ); ?></p>
</div>
11
  • Comments are not for extended discussion; this conversation has been moved to chat.
    – Howdy_McGee
    Aug 23, 2017 at 18:17
  • @ClemC see the update.
    – Vucko
    Aug 26, 2017 at 8:44
  • @Vucko see the update.
    – ClemC
    Aug 26, 2017 at 9:53
  • It prints the div and the p, but the p is empty.
    – Vucko
    Aug 26, 2017 at 9:55
  • var_dump(get_post_meta( $post->ID, 'my_text_field', true )) returns string(0) "" even if my custom field has a saved string.
    – Vucko
    Aug 26, 2017 at 10:02

Not the answer you're looking for? Browse other questions tagged or ask your own question.