Отобразить нефильтрованную страницу ниже отфильтрованной

Вопрос или проблема

Я добавил атрибуты для фильтрации продуктов на основе их выбора. Например, у меня есть поле с названием ‘плитка’, которое может быть ‘да’ или ‘нет’. Если человек ставит галочку ‘да’, показываются все продукты с атрибутом ‘да’. Все продукты с атрибутом ‘нет’ не отображаются.

Как я могу отобразить все продукты, которые не отфильтрованы, НИЖЕ отфильтрованного запроса (т.е. показывая все продукты с ‘нет’ под фильтром продукта)?

Внутри моего файла functions.php, я полагаю, что вот как осуществляются запросы отфильтрованных продуктов:

function sort_products_by_positive_attributes($query) {
    if (!is_admin() && $query->is_main_query() && is_woocommerce()) {
        // Сначала вам нужно получить все продукты вместе с количеством их положительных атрибутов
        $products_with_scores = [];
         if (!empty($query->posts)) {
        foreach ($query->posts as $post) {
            $product = wc_get_product($post->ID);
            $score = get_product_positive_attributes_count($product);
            $products_with_scores[$post->ID] = $score;
        }
        }else {

        }
        // Затем вы бы отсортировали продукты по их баллу
        uasort($products_with_scores, function($a, $b) {
            return $b - $a;
        });

        // После сортировки измените запрос, чтобы упорядочить по ID в отсортированном порядке
        $sorted_ids = array_keys($products_with_scores);
        $query->set('orderby', 'post__in');
        $query->set('post__in', $sorted_ids);

        // Запрос для отображения неотфильтрованных здесь

    }
}
//add_action('pre_get_posts', 'sort_products_by_positive_attributes');

function get_product_positive_attributes_count($product) {
    // Вы бы реализовали логику здесь для подсчета количества положительных атрибутов
    $score = 0;
    // для каждого атрибута, если он положительный, увеличьте $score
    return $score;
}

Ответ или решение

Чтобы отобразить все продукты, не прошедшие фильтр, ниже отфильтрованного списка на вашем сайте WooCommerce, необходимо внести изменения в функцию sort_products_by_positive_attributes, чтобы учесть и неотфильтрованные товары. В данной статье мы подробно рассмотрим, как добиться такого поведения в WordPress через отладку и корректировку кода, что обеспечит необходимый функционал.

Шаг 1: Изменение функции фильтрации продуктов

В вашей функции, которая уже отвечает за фильтрацию продуктов, необходимо добавить дополнительный запрос, который будет извлекать продукты, у которых атрибут ‘tiled’ установлен на ‘no’. Для этого воспользуемся особенностями WP_Query.

Вот как можно изменить вашу функцию:

function sort_products_by_positive_attributes($query) {
    if (!is_admin() && $query->is_main_query() && is_woocommerce()) {

        // Получаем все продукты, которые соответствуют положительным атрибутам
        $products_with_scores = [];
        if (!empty($query->posts)) {
            foreach ($query->posts as $post) {
                $product = wc_get_product($post->ID);
                $score = get_product_positive_attributes_count($product);
                $products_with_scores[$post->ID] = $score;
            }
        }

        // Сортировка продуктов по количеству положительных атрибутов
        uasort($products_with_scores, function($a, $b) {
            return $b - $a;
        });

        // Получаем ID отфильтрованных продуктов
        $sorted_ids = array_keys($products_with_scores);
        $query->set('orderby', 'post__in');
        $query->set('post__in', $sorted_ids);

        // Запрос на извлечение неотфильтрованных продуктов
        $non_filtered_query = new WP_Query([
            'post_type' => 'product',
            'posts_per_page' => -1, // Выведем все
            'tax_query' => [
                [
                    'taxonomy' => 'pa_tiled', // Замените на правильное имя таксономии
                    'field' => 'slug',
                    'terms' => 'no', // Запрос продуктов с атрибутом 'no'
                    'operator' => 'IN'
                ]
            ],
            'post__not_in' => $sorted_ids // Исключаем уже отфильтрованные товары
        ]);

        // Сохраняем все ID из неотфильтрованных запросов, чтобы позже объединить результаты
        if ($non_filtered_query->have_posts()) {
            $non_filtered_ids = wp_list_pluck($non_filtered_query->posts, 'ID');
            // Объединяем ID отфильтрованных и неотфильтрованных товаров
            $final_ids = array_merge($sorted_ids, $non_filtered_ids);
            $query->set('post__in', $final_ids);
        }
    }
}
add_action('pre_get_posts', 'sort_products_by_positive_attributes');

function get_product_positive_attributes_count($product) {
    $score = 0;
    // Здесь вы можете реализовать логику подсчета положительных атрибутов
    return $score;
}

Шаг 2: Объяснение кода

В первой части мы устанавливаем условия, при которых функция будет работать только на сторонних страницах WooCommerce. Затем мы собираем и сортируем ID отфильтрованных продуктов.

Во втором ключевом моменте мы создаем новый запрос WP_Query, который обращается к тем продуктам, у которых атрибут ‘tiled’ установлен на значение ‘no’. Это позволяет нам извлечь все продукты, не прошедшие фильтрацию.

Используя post__not_in, мы отфильтровываем уже извлеченные продукты, чтобы избежать дублирования. В конце функция объединяет ID отфильтрованных и неотфильтрованных товаров и обновляет основной запрос.

Заключение

Данная модификация кода обеспечит функционал отображения всех продуктов, у которых атрибут ‘tiled’ равен ‘no’, под уже отфильтрованным списком продуктов. Это улучшит пользовательский опыт на сайте и позволит клиентам легче ориентироваться в вашем товарном предложении.

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

Оцените материал
Добавить комментарий

Капча загружается...