Manuel Orozco Jimenez
Manuel Orozco Jimenez

Reputation: 105

Show multiple product custom fields values in cart on Woocommerce

I have a problem with custom fields & values from my product page appearing on the cart page. As you can see from the screenshots, I have three fields: "Color," "Texto1" and "Texto2" and only the first seems to appear on my cart page.

This is the code that print the fields on the product page:

// Field 1
if( ! empty( $FieldType1 ) ){
    if( $FieldType1 == "TEXT AREA"){
    echo '<div>
        <label>'.$FieldName1.':<br></label> <textarea name="FieldTypeValue1" maxlength="'.$FieldLenght1.'" rows="2" cols="80" placeholder="" required></textarea>
    </div><br>';
    }

    if( $FieldType1 == "TEXT BOX"){
    echo '<div>
        <label>'.$FieldName1.':<br></label> <input type="text"  maxlength="'.$FieldLenght1.'" name="FieldTypeValue1" value="" required>
    </div><br>';
    }

    if( $FieldType1 == "DROP DOWN"){
        echo '<div>
        <label>'.$FieldName1.':<br></label>
        <select name="FieldTypeValue1">';
        foreach ($Dropdown1Content as $Dropdown1IndividualContent) {
        echo '<option>';
        echo $Dropdown1IndividualContent;
        echo '</option>';
        }

        echo '</select></div><br>';
    }
}

// Field 2  
if( ! empty( $FieldType2 ) ){
    if( $FieldType2 == "TEXT AREA"){
    echo '<div>
        <label>'.$FieldName2.':<br></label> <textarea name="FieldTypeValue2" maxlength="'.$FieldLenght2.'" rows="2" cols="80" placeholder="" required></textarea>
    </div><br>';
    }

    if( $FieldType2 == "TEXT BOX"){
    echo '<div>
        <label>'.$FieldName2.':<br></label> <input type="text"  maxlength="'.$FieldLenght2.'" name="FieldTypeValue2" value="" required>
    </div><br>';
    }

    if( $FieldType2 == "DROP DOWN"){
        echo '<div>
        <label>'.$FieldName2.':<br></label>
        <select name="FieldTypeValue2">';
        foreach ($Dropdown2Content as $Dropdown2IndividualContent) {
        echo '<option>';
        echo $Dropdown2IndividualContent;
        echo '</option>';
        }

        echo '</select></div><br>';
    }
}



// Field 3
if( ! empty( $FieldType3 ) ){
    if( $FieldType3 == "TEXT AREA"){
    echo '<div>
        <label>'.$FieldName3.':<br></label> <textarea name="FieldTypeValue3" maxlength="'.$FieldLenght3.'" rows="2" cols="80" placeholder="" required></textarea>
    </div><br>';
    }

    if( $FieldType3 == "TEXT BOX"){
    echo '<div>
        <label>'.$FieldName3.':<br></label> <input type="text"  maxlength="'.$FieldLenght3.'" name="FieldTypeValue3" value="" required>
    </div><br>';
    }

    if( $FieldType3 == "DROP DOWN"){
        echo '<div>
        <label>'.$FieldName3.':<br></label>
        <select name="FieldTypeValue3">';
        foreach ($Dropdown3Content as $Dropdown3IndividualContent) {
        echo '<option>';
        echo $Dropdown3IndividualContent;
        echo '</option>';
        }

        echo '</select></div><br>';
    }
}

This is the code that saves the value of the fields on the product page

// Store custom field label and value in cart item data
add_action( 'woocommerce_add_cart_item_data','save_my_custom_checkout_field', 10, 2 );
function save_my_custom_checkout_field( $cart_item_data, $product_id ) {
if( isset( $_REQUEST['FieldTypeValue1'] ) ) {
    $cart_item_data['custom_data']['label'] = get_post_meta($product_id, 'FieldName1', true);
    $cart_item_data['custom_data']['value'] = sanitize_text_field( $_REQUEST['FieldTypeValue1'] );
    $cart_item_data['custom_data']['ukey'] = md5( microtime().rand() );
}
return $cart_item_data;

if( isset( $_REQUEST['FieldTypeValue2'] ) ) {
    $cart_item_data['custom_data']['label'] = get_post_meta($product_id, 'FieldName2', true);
    $cart_item_data['custom_data']['value'] = sanitize_text_field( $_REQUEST['FieldTypeValue2'] );
    $cart_item_data['custom_data']['ukey'] = md5( microtime().rand() );
}
return $cart_item_data;

if( isset( $_REQUEST['FieldTypeValue3'] ) ) {
    $cart_item_data['custom_data']['label'] = get_post_meta($product_id,'FieldName3', true);
    $cart_item_data['custom_data']['value'] = sanitize_text_field( $_REQUEST['FieldTypeValue3'] );
    $cart_item_data['custom_data']['ukey'] = md5( microtime().rand() );
}
return $cart_item_data;

And this is the one that print the values on the cart:

// Display items custom fields label and value in cart and checkout pages
add_filter( 'woocommerce_get_item_data', 'render_meta_on_cart_and_checkout', 10, 2 );
function render_meta_on_cart_and_checkout( $cart_data, $cart_item ){

$custom_items = array();

/* Woo 2.4.2 updates */
if( !empty( $cart_data ) ) {
    $custom_items = $cart_data;
}
if( isset( $cart_item['custom_data'] ) ) {
    $custom_items[] = array(
        'name' => $cart_item['custom_data']['label'],
        'value' => $cart_item['custom_data']['value'],
    );
}
return $custom_items;

}

The Custom fields on product page:

Product page

The product in cart (with the missing data):

Product in cart

I'm not sure if the problem is at the point where values are saved or at the point where they are printed.

Any help would be much appreciated.

Upvotes: 3

Views: 1319

Answers (1)

LoicTheAztec
LoicTheAztec

Reputation: 254373

Try this hooked functions instead, where I have revisited your code to make it work:

// Store custom field label and value in cart item data
add_filter( 'woocommerce_add_cart_item_data','save_my_custom_checkout_field', 20, 2 );
function save_my_custom_checkout_field( $cart_item_data, $product_id ) {
    $label1 = get_post_meta( $product_id, 'FieldName1', true );
    $label2 = get_post_meta( $product_id, 'FieldName2', true );
    $label3 = get_post_meta( $product_id, 'FieldName3', true );

    if( isset( $_REQUEST['FieldTypeValue1'] ) && ! empty( $label1 ) )
        $cart_item_data['custom_data']['1'] = array(
            'label' => $label1,
            'value' => sanitize_text_field( $_REQUEST['FieldTypeValue1'] ),
        );

    if( isset( $_REQUEST['FieldTypeValue2'] ) && ! empty( $label2 ) )
        $cart_item_data['custom_data']['2'] = array(
            'label' => $label2,
            'value' => sanitize_text_field( $_REQUEST['FieldTypeValue2'] ),
        );

    if( isset( $_REQUEST['FieldTypeValue3'] ) && ! empty( $label3 ) )
        $cart_item_data['custom_data']['3'] = array(
            'label' => $label3,
            'value' => sanitize_text_field( $_REQUEST['FieldTypeValue3'] ),
        );

    if( count($cart_item_data['custom_data']) > 0 )
        $cart_item_data['custom_data']['key'] = md5( microtime().rand() );

    return $cart_item_data;
}

// Display items custom fields label and value in cart and checkout pages
add_filter( 'woocommerce_get_item_data', 'render_meta_on_cart_and_checkout', 20, 2 );
function render_meta_on_cart_and_checkout( $cart_data, $cart_item ){
    $custom_items = array();

    if( !empty( $cart_data ) )
        $custom_items = $cart_data;

    if( isset( $cart_item['custom_data'] ) ) {
        foreach( $cart_item['custom_data'] as $key => $custom_data ){
            if( $key != 'key' ){
                $custom_items[] = array(
                    'name' => $custom_data['label'],
                    'value' => $custom_data['value'],
                );
            }
        }
    }
    return $custom_items;
}

Code goes in function.php file of your active child theme (or active theme).

Tested and works… You will get something like that:

enter image description here


For testing I have used the following to display the 3 custom fields on single product page:

// Displaying 3 custom fields on single product pages
add_action( 'woocommerce_before_add_to_cart_button', 'add_custom_fields_single_product', 20 );
function add_custom_fields_single_product(){
    global $product;

    echo '<div>
    <label>'.__('Color').': </label><br>
    <input type="text" name="FieldTypeValue1" value="" required>
</div><br>';
    echo '<div>
    <label>'.__('Texto 1').': </label><br>
    <input type="text" name="FieldTypeValue2" value="" required>
</div><br>';
    echo '<div>
    <label>'.__('Texto 2').': </label><br>
    <input type="text" name="FieldTypeValue3" value="" required>
</div><br>';
}

Changing the following for testing purpose only (in the functions code):

    $label1 = get_post_meta( $product_id, 'FieldName1', true );
    $label2 = get_post_meta( $product_id, 'FieldName2', true );
    $label3 = get_post_meta( $product_id, 'FieldName3', true );

by:

    $label1 = __('Color'); 
    $label2 = __('Texto 1'); 
    $label3 = __('Texto 2'); 

Upvotes: 1

Related Questions