Magento – How to change price for configurable products in Product Listing using drop down options in Magento 2

configurable-productmagento2moduleprice

I have created a custom module in magento2, and I want to show configurable products options in the drop-down for the configurable product.

I have done using custom code, but problem is that when I change the option for a configurable product the price does not change anything.

Could you please let me know what we need to do to show the change price on the change that is related to the dropdown?

<form data-product-sku="<?= /* @NoEscape */ $product->getSku() ?>"
      action="<?= /* @NoEscape */ $block->getSubmitUrl($product) ?>" method="post"
      id="product_addtocart_form"<?php if ($product->getOptions()): ?> enctype="multipart/form-data"<?php endif; ?>>
    <input type="hidden" name="product" value="<?= /* @escapeNotVerified */ $product->getId() ?>" />
    <input type="hidden" name="selected_configurable_option" value="" />
    <input type="hidden" name="related_product" id="related-products-field" value="" />
  
    <?= $block->getChildHtml('form_top') ?>
    <?php if (!$block->hasOptions()):?>
        <?= $block->getChildHtml('product_info_form_content') ?>
    <?php else:?>
        <?php if ($_product->isSaleable() && $block->getOptionsContainer() == 'container1'):?>
            <?= $block->getChildChildHtml('options_container') ?>
        <?php endif;?>
    <?php endif; ?>

     <?= $block->getBlockHtml('formkey'); ?>
    <div class="product-options-wrapper" id="product-options-wrapper" data-hasrequired="* Verplichte velden">
    <?php if($product->getTypeId() === 'configurable') : ?>
        <?php foreach($product->getTypeInstance()->getConfigurableAttributes($product) as $attribute) : ?>
            <div class="field configurable required">
                <label class="label" for="attribute<?php echo $attribute->getAttributeId(); ?>"><span><?php echo $attribute->getLabel() ?></span></label>
                <?php $values = $attribute->getOptions(); ?>
                <div class="control">
                    <select id="attribute<?php echo $attribute->getAttributeId() ?>" name="super_attribute[<?php echo $attribute->getAttributeId() ?>]" class="super-attribute-select upsell_options" data-validate="{required:true}">
                        <option value="">Choose an Option...</option>
                        <?php foreach($values as $value): ?>

                            <option value="<?php echo $value['value_index'] ?>" ><?php echo  $value['label'] ?></option>

                        <?php endforeach; ?>

                    </select>
                </div>
            </div>
        <?php endforeach; ?>

        <?php 
   
        ?>
      <?php endif; ?>
      </div> 
    <?= $block->getChildHtml('form_bottom') ?>
</form>

 <script>
require([
    'jquery',
    'priceBox'
], function($){
    var dataPriceBoxSelector = '[data-role=priceBox]',
        dataProductIdSelector = '[data-product-id=<?= $block->escapeHtml($product->getId()) ?>]',
        priceBoxes = $(dataPriceBoxSelector + dataProductIdSelector);

    priceBoxes = priceBoxes.filter(function(index, elem){
        return !$(elem).find('.price-from').length;
    });

    priceBoxes.priceBox({'priceConfig': <?= /* @escapeNotVerified */ $block->getJsonConfig() ?>});
});

Best Answer

You've to add some code to change the price while changing the drop-down, that file path is www\app\design\frontend\XXX\XXX\Magento_Swatches\web\js, after adding, please do setup upgrade and content-deploy

  • Step-1: Add Following code in _EventListener: function () {

    $widget.element.on('change', '.' + this.options.classes.selectClass, function () {
        return $widget._OnChangeCustom($(this), $widget);
    });
    
  • Step-2: Add this function

    _OnChangeCustom: function ($this, $widget) {
        var check = $this.val();
        var checkId = '#'+$this.parent().attr('id');
        $(checkId+' option').each(function(){
            var currentValue = $(this).val();
            if(currentValue == check){
                $(this).attr('selected', true);
                $(this).addClass('selected');
                var currentId = $(this).attr('option-id');
                $(checkId+' select').attr('option-selected',currentId);
            }else{
                $(this).removeClass('selected');
                $(this).attr('selected', false);
            }
        });
        $widget._Rebuild();
    
        if ($widget.element.parents($widget.options.selectorProduct)
                .find(this.options.selectorProductPrice).is(':data(mage-priceBox)')
        ) {
            $widget._UpdatePrice();
        }
    
        $widget._LoadProductMedia();
    
    },
    
  • Step-3: Add this function

     _LoadProductMedia: function () {
        var $widget = this,
            $this = $widget.element,
            attributes = {},
            productId = 0;
    
        if (!$widget.options.mediaCallback) {
            return;
        }
    
        $this.find('[option-selected]').each(function () {
            var $selected = $(this);
            attributes[$selected.attr('attribute-code')] = $selected.attr('option-selected');
        });
    
        if ($('body.catalog-product-view').size() > 0) {
            //Product Page
            productId = document.getElementsByName('product')[0].value;
        } else {
            //Category View
            //create productId hidden field from list.phtml
            productId = $this.parents('.product.details.product-item-details').find('#productId').val();
        }
    
        var additional = $.parseParams(window.location.search.substring(1));
    
        $widget._XhrKiller();
        $widget._EnableProductMediaLoader($this);
        $widget.xhr = $.post(
            $widget.options.mediaCallback,
            {product_id: productId, attributes: attributes, isAjax: true, additional: additional},
            function (data) {
                var newPrice = data.special;
                var oldPrice = data.price;
                // ** add your price html here to update **
                $widget._ProductMediaCallback($this, data);
                $widget._DisableProductMediaLoader($this);
            },
            'json'
        ).done(function () {
            $widget._XhrKiller();
        });
    },
    
Related Topic