Add a select field that will change price in Woocommerce simple products

Add a select field that will change price in Woocommerce simple products

To add a select field in simple products (like in variable products) that will update base price depending on the dopdown selected value, try this:

<?php
  // Frontend: custom select field in product single pages
  add_action( 'woocommerce_before_add_to_cart_button', 'fabric_length_product_field' );

  function fabric_length_product_field() {
      global $product;

      if( $product->is_type('variable') ) return; // Not variable products

      $domain = 'woocommerce';
      $text   = array(
          __('cards', $domain),
          __('card', $domain),
          __('Total', $domain),
          get_woocommerce_currency_symbol(),
      );

      // Select Options array
      $options = array(
          ""          => __('Select package'),
          "12.00" => "1000 {$text[0]} - {$text[3]}0.012/{$text[1]} - {$text[2]} {$text[3]}12.00",
          "15.00" => "2000 {$text[0]} - {$text[3]}0.008/{$text[1]} - {$text[2]} {$text[3]}15.00",
          "20.00" => "3000 {$text[0]} - {$text[3]}0.007/{$text[1]} - {$text[2]} {$text[3]}20.00",
          "25.00" => "4000 {$text[0]} - {$text[3]}0.006/{$text[1]} - {$text[2]} {$text[3]}25.00",
      );

      // Select field
      woocommerce_form_field('cards_pack', array(
          'type'          => 'select',
          'class'         => array('my-field-class form-row-wide'),
          'label'         => __('Cards Pack selection', $domain),
          'required'      => true,
          'options'       => $options,
      ),'');

      // Data to be transmitted to jQuery
      $base_price = (float) wc_get_price_to_display( $product );
      $prices = array(
          ''      => wc_price($base_price),
          '12.00' => wc_price($base_price + 12),
          '15.00' => wc_price($base_price + 15),
          '20.00' => wc_price($base_price + 20),
          '25.00' => wc_price($base_price + 25),
      )

      // jQuery code
      ?>
      <script>
      jQuery(function($){
          var a = <?php echo json_encode($prices); ?>,
              b = 'p.price',
              c = 'select[name="cards_pack"]';

          $(c).on( 'change', function(){
              $.each( a, function( key, value ){
                  if( $(c).val() == key )
                      $(b).html(value);
              });
          });
      });
      </script>
      <?php
  }

  // Add selected pack data as custom data to cart items
  add_filter( 'woocommerce_add_cart_item_data', 'add_pack_data_to_cart_item_data', 20, 2 );

  function add_pack_data_to_cart_item_data( $cart_item_data, $product_id ){
      if( ! isset($_POST['cards_pack']) )
          return $cart_item_data;

      $pack_price = (float) sanitize_text_field( $_POST['cards_pack'] );
      if( empty($pack_price) )
          return $cart_item_data;

      if($pack_price == 12.00) $cards = 1000;
      elseif($pack_price == 15.00) $cards = 2000;
      elseif($pack_price == 20.00) $cards = 3000;
      elseif($pack_price == 25.00) $cards = 4000;

      $product    = wc_get_product($product_id); // The WC_Product Object
      $base_price = (float) $product->get_price();

      // New price calculation
      $new_price = $base_price + $pack_price;

      // Prepare and save the data array
      $cart_item_data['pack_data'] = array(
          'cards'     => (int)   $cards,
          'pack'      => (int)   $pack_price,
          'new_price' => (float) $new_price,
      );
      $cart_item_data['unique_key'] = md5( microtime() . rand() ); // Make each item unique

      return $cart_item_data;
  }

  // Set conditionally a custom item price
  add_action('woocommerce_before_calculate_totals', 'set_cutom_cart_item_price', 20, 1);

  function set_cutom_cart_item_price( $cart ) {
      if ( is_admin() && ! defined( 'DOING_AJAX' ) )
          return;

      if ( did_action( 'woocommerce_before_calculate_totals' ) >= 2 )
          return;

      foreach (  $cart->get_cart() as $cart_item ) {
          if ( isset( $cart_item['pack_data']['new_price'] ) )
              $cart_item['data']->set_price( $cart_item['pack_data']['new_price'] );
      }
  }


  // Display custom data in  checkout page
  add_filter( 'woocommerce_get_item_data', 'display_custom_cart_item_data', 10, 2 );

  function display_custom_cart_item_data( $cart_data, $cart_item ) {
      $domain        = 'woocommerce';

      if ( isset( $cart_item['pack_data']['new_price'] ) ){
          $cart_data[] = array('name' => __( 'Cards pack', $domain ),
              'value' => $cart_item['pack_data']['cards'] );
      }
      return $cart_data;
  }
?>

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

Was this article helpful?
YesNo

Leave a comment

Your email address will not be published. Required fields are marked *