Woocommerce - Страница продукта - Как создать AJAX на кнопке "Добавить в корзину"?

Я хочу сделать кнопку "Добавить в корзину" на странице продукта, которая будет работать с AJAX. Как мне это сделать? Когда я добавляю в корзину на странице товара - она обновляет страницу, как я могу заставить ее работать с помощью AJAX?

Кнопка "Добавить в корзину" на "Быстрый просмотр" в архиве работает от ajax - и это здорово, но как я могу сделать то же самое на странице продукта?

Я хочу нажать "Отвези меня домой" на странице продукта, которая затем добавит продукт с выбранными атрибутами в мою корзину с помощью ajax и откроет эту корзину (как при наведении курсора на изображение сумки в меню) и потрясет сумку. образ.

Ответ 1

Мы можем использовать ajax из архивной страницы. это легко -

Удалите старую кнопку, которая представляет форму:

remove_action( 'woocommerce_single_product_summary', 'woocommerce_template_single_add_to_cart', 30 );

Добавить ajax-ссылку с страницы архива на страницу одного продукта:

add_action( 'woocommerce_single_product_summary', 'woocommerce_template_loop_add_to_cart', 30 );

P.S. Обратный вызов JS. Например, вы можете отображать всплывающее окно со ссылками "Назад в магазин" и "Корзина" или "Оформить заказ"

$('body').on('added_to_cart',function(){
    // Callback -> product added
    //$('.popup').show();
});

Ответ 2

Пожалуйста, начните с чтения этой страницы:

http://codex.wordpress.org/Plugin_API/Action_Reference/wp_ajax_(action)

Сначала вам нужно добавить код в свой файл functions.php, например:

add_action( 'wp_ajax_add_foobar', 'prefix_ajax_add_foobar' );
add_action( 'wp_ajax_nopriv_add_foobar', 'prefix_ajax_add_foobar' );

function prefix_ajax_add_foobar() {
   $product_id  = intval( $_POST['product_id'] );
// add code the add the product to your cart
die();
}

Затем вам нужно добавить код javascript, который запускает добавление в корзину и вызывает вызов функции:

  jQuery( ".add-to-cart" ).each(function() 
{


    var product_id = jQuery(this).attr('rel');
    var el = jQuery(this);

    el.click(function() {

            var data = {
                action: 'add_foobar',
                product_id: product_id
            };

            jQuery.post('/wp-admin/admin-ajax.php' , data, function(response) {
                if(response != 0) {
                    // do something
                } else {
                    // do something else
                }

            });


        return false;

    });

});

Это просто пример того, как это можно сделать. Хотя его очень простой. Этот javascript проверяет ссылки с именем класса .add-to-cart и проверяет атрибут rel для соответствующего продукта. Затем он отправляет идентификатор продукта в класс php. Там вам нужно добавить код, чтобы добавить соответствующий товар в корзину.

Я предлагаю вам найти более подробную информацию о теме, чтобы она соответствовала вашим потребностям. Удачи.

Ответ 3

info: Протестировано с WooCommerce 2.4.10.

Хм, хорошо, я сделал это по-другому, использовал петлю woocommerce из добавления в корзину (woocommerce/templates/loop/add-to-cart.php)

  global $product;

echo apply_filters( 'woocommerce_loop_add_to_cart_link',
    sprintf( '<a href="%s" rel="nofollow" data-product_id="%s" data-product_sku="%s" data-quantity="%s" class="button %s product_type_%s">%s</a>',
        esc_url( $product->add_to_cart_url() ),
        esc_attr( $product->id ),
        esc_attr( $product->get_sku() ),
        esc_attr( isset( $quantity ) ? $quantity : 1 ),
        $product->is_purchasable() && $product->is_in_stock() ? 'add_to_cart_button' : '',
        esc_attr( $product->product_type ),
        esc_html( $product->add_to_cart_text() )
    ),
$product );

НО проблема заключалась в том, что она добавляла только 1 количество, по сути, вы можете видеть в коде, который указан в количестве: 1, поэтому у меня были проблемы, пока я не столкнулся с эти ребята, которые спасли меня

пс. оставив 1-ю часть, где он добавляет только 1 продукт для людей, которым не нужно больше 1 продукта в корзине, но я добавил решение для тех, кому нужно больше, чем только один продукт, добавленный в корзину.

Ответ 4

добавить к cart.js

jQuery( document ).on( 'click', '.product_type_simple', function() { 

var post_id = jQuery(this).data('product_id');//store product id in post id variable
var qty = jQuery(this).data('quantity');//store quantity in qty variable

jQuery.ajax({
    url : addtocart.ajax_url, //ajax object of localization
    type : 'post', //post method to access data
    data : 
    {
        action : 'prefix_ajax_add_foobar', //action on prefix_ajax_add_foobar function
        post_id : post_id,
        quantity: qty
    },

    success : function(response){

            jQuery('.site-header .quantity').html(response.qty);//get quantity
            jQuery('.site-header .total').html(response.total);//get total

            //loaderContainer.remove();
            alert("Product Added successfully..");        
    }

});

return false;
});

Ответ 5

Скопируйте этот код в свой файл. Например: my-theme-wc-single-ajax-add-cart.js.

function myThemeWc_SingleProductAddToCart(thisObj) {
    if (typeof($) === 'undefined') {
        var $ = jQuery.noConflict();
    }

    var thisForm = thisObj.closest('form');
    var button = thisForm.find('.button');
    var formUrl = thisForm.attr('action');
    var formMethod = thisForm.attr('method');
    if (typeof(formMethod) === 'undefined' || formMethod == '') {
        formMethod = 'POST';
    }
    var formData = new FormData(thisForm[0]);
    formData.append(button.attr('name'), button.val());

    button.removeClass('added');
    button.addClass('loading');

    myThemeWc_SingleProductCartAjaxTask = $.ajax({
        url: formUrl,
        method: formMethod,
        data: formData,
        cache: false,
        contentType: false,
        processData: false
    })
    .done(function(data, textStatus, jqXHR) {
        $(document.body).trigger('wc_fragment_refresh');

        $.when(myThemeWc_SingleProductCartAjaxTask)
        .then(myThemeWc_SingleProductUpdateCartWidget)
        .done(function() {
            button.removeClass('loading');
            button.addClass('added');
            setTimeout(function() {
                button.removeClass('added');
            }, 2000);
        });
    })
    .fail(function(jqXHR, textStatus, errorThrown) {
        button.removeClass('loading');
    })
    .always(function(jqXHR, textStatus, errorThrown) {
        $('.cart').off('submit');
        myThemeWc_SingleProductListenAddToCart();
    });
}// myThemeWc_SingleProductAddToCart


function myThemeWc_SingleProductListenAddToCart() {
    if (typeof($) === 'undefined') {
        var $ = jQuery.noConflict();
    }

    $('.cart').on('submit', function(e) {
        e.preventDefault();
        myThemeWc_SingleProductAddToCart($(this));
    });
}// myThemeWc_SingleProductListenAddToCart


/**
 * Update WooCommerce cart widget by called the trigger and listen to the event.
 * 
 * @returns {undefined}
 */
function myThemeWc_SingleProductUpdateCartWidget() {
    if (typeof($) === 'undefined') {
        var $ = jQuery.noConflict();
    }

    var deferred = $.Deferred();

    $(document.body).on('wc_fragments_refreshed', function() {
        deferred.resolve();
    });

    return deferred.promise();
}// myThemeWc_SingleProductUpdateCartWidget


var myThemeWc_SingleProductCartAjaxTask;


// on page load --------------------------------------------
jQuery(function($) {
    $(document.body).on('wc_fragments_refreshed', function() {
        console.log('woocommerce event fired: wc_fragments_refreshed');
    });

    myThemeWc_SingleProductListenAddToCart();
});

Возможно, вам придется заменить функцию, префикс переменной myThemeWc_ на то, что вы хотите.

Этот код использует оригинальную страницу продукта WooCommerce для добавления кнопки в корзину, но останавливает ее функционирование и затем использует ajax, оставляя все значения в форме.

Затем поставьте в очередь этот файл js.

add_action('wp_enqueue_scripts', 'mythemewc_enqueue_scripts');
function mythemewc_enqueue_scripts() {
    if (class_exists('\\WooCommerce') && is_product()) {
        wp_enqueue_script('mythemewc-single-product', trailingslashit(get_stylesheet_directory_uri()) . 'assets/js/my-theme-wc-single-ajax-add-cart.js', ['jquery'], false, true);
    }
}

Возможно, вам придется кодировать кнопку css, чтобы она отображала значок загрузки и добавления.
Вот ксс.

.woocommerce #respond input#submit.added::after, 
.woocommerce a.btn.added::after, 
.woocommerce button.btn.added::after, 
.woocommerce input.btn.added::after,
.woocommerce .single_add_to_cart_button.added::after {
    font-family: WooCommerce;
    content: '\e017';
    margin-left: .53em;
    vertical-align: bottom;
}
.woocommerce #respond input#submit.loading, 
.woocommerce a.btn.loading, 
.woocommerce button.btn.loading, 
.woocommerce input.btn.loading,
.woocommerce .single_add_to_cart_button.loading {
    opacity: .25;
    padding-right: 2.618em;
    position: relative;
}
.woocommerce #respond input#submit.loading::after, 
.woocommerce a.btn.loading::after, 
.woocommerce button.btn.loading::after, 
.woocommerce input.btn.loading::after,
.woocommerce .single_add_to_cart_button.loading::after {
    font-family: WooCommerce;
    content: '\e01c';
    vertical-align: top;
    font-weight: 400;
    position: absolute;
    right: 1em;
    -webkit-animation: spin 2s linear infinite;
    animation: spin 2s linear infinite;
}

Ответ 6

Вы можете повторить поведение кнопки архивирования в ваших продуктах.

add_action('wp_ajax_woocommerce_ajax_add_to_cart', 'woocommerce_ajax_add_to_cart');
add_action('wp_ajax_nopriv_woocommerce_ajax_add_to_cart', 'woocommerce_ajax_add_to_cart');      function woocommerce_ajax_add_to_cart() {
            $product_id = apply_filters('woocommerce_add_to_cart_product_id', absint($_POST['product_id']));
            $quantity = empty($_POST['quantity']) ? 1 : wc_stock_amount($_POST['quantity']);
            $variation_id = absint($_POST['variation_id']);
            $passed_validation = apply_filters('woocommerce_add_to_cart_validation', true, $product_id, $quantity);
            $product_status = get_post_status($product_id);

            if ($passed_validation && WC()->cart->add_to_cart($product_id, $quantity, $variation_id) && 'publish' === $product_status) {

                do_action('woocommerce_ajax_added_to_cart', $product_id);

                if ('yes' === get_option('woocommerce_cart_redirect_after_add')) {
                    wc_add_to_cart_message(array($product_id => $quantity), true);
                }

                WC_AJAX :: get_refreshed_fragments();
            } else {

                $data = array(
                    'error' => true,
                    'product_url' => apply_filters('woocommerce_cart_redirect_after_error', get_permalink($product_id), $product_id));

                echo wp_send_json($data);
            }

            wp_die();
        }
add_action('wp_ajax_woocommerce_ajax_add_to_cart', 'woocommerce_ajax_add_to_cart');
add_action('wp_ajax_nopriv_woocommerce_ajax_add_to_cart', 'woocommerce_ajax_add_to_cart');

function woocommerce_ajax_add_to_cart() {

            $product_id = apply_filters('woocommerce_add_to_cart_product_id', absint($_POST['product_id']));
            $quantity = empty($_POST['quantity']) ? 1 : wc_stock_amount($_POST['quantity']);
            $variation_id = absint($_POST['variation_id']);
            $passed_validation = apply_filters('woocommerce_add_to_cart_validation', true, $product_id, $quantity);
            $product_status = get_post_status($product_id);

            if ($passed_validation && WC()->cart->add_to_cart($product_id, $quantity, $variation_id) && 'publish' === $product_status) {

                do_action('woocommerce_ajax_added_to_cart', $product_id);

                if ('yes' === get_option('woocommerce_cart_redirect_after_add')) {
                    wc_add_to_cart_message(array($product_id => $quantity), true);
                }

                WC_AJAX :: get_refreshed_fragments();
            } else {

                $data = array(
                    'error' => true,
                    'product_url' => apply_filters('woocommerce_cart_redirect_after_error', get_permalink($product_id), $product_id));

                echo wp_send_json($data);
            }

            wp_die();
        }

Вы можете увидеть полный учебник здесь

https://quadmenu.com/add-to-cart-with-woocommerce-and-ajax-step-by-step/

Ответ 7

Woocommerce прошла путь. Я думаю, что решение довольно легко сейчас. В случае, если я что-то упустил, все, что требуется, это проверить "Включить кнопки добавления AJAX в корзину в архивах" и использовать woocommerce_template_loop_add_to_cart().

Опция флажка находится в Woocommerce> Настройки> Продукты> Общие. The checkbox option is under Woocommerce > Settings > Products > General.

Затем просто используйте woocommerce_template_loop_add_to_cart() везде, где вы хотите вывести кнопку.

Если вы используете пользовательский цикл, как я, вам нужно сделать продукт глобальным, чтобы woocommerce_template_loop_add_to_cart() работал.

Ниже приведен небольшой пример использования функции:

add_shortcode( 'buy_again' , 'msp_buy_again_shortcode' );
function msp_buy_again_shortcode(){
    $order_items = msp_get_customer_unique_order_items( get_current_user_id() );
    echo '<div class="owl-carousel owl-theme">';
    foreach( $order_items as $id ){
        $product = wc_get_product( $id );
        global $product;

        if( ! empty( $product ) ){
            ?>
            <div class="card buy-again-product">
                <a class="link-normal" href="<?php echo $product->get_permalink(); ?>">
                    <?php echo $product->get_image( 'woocommerce_thumbnail', array( 'class' => 'card-img-top' ) ) ?>
                    <div class="card-body">
                        <?php echo wc_get_rating_html( $product->get_average_rating(), $product->get_review_count() ) ?>
                        <h5><?php echo $product->get_name(); ?></h5>
                        <p><?php echo $product->get_price_html() ?></p>
                        <?php woocommerce_template_loop_add_to_cart(); ?>
                    </div>
                </a>
            </div>
            <?php
        }
    }
    // loop and display buy again.
    // try to use the official woocommerce loop.

    echo '</div>';

}