Вопрос или проблема
Я искал решение повсюду и не смог ничего найти; надеюсь, кто-то здесь более умеющий, чем я, сможет помочь.
У меня есть два видеоотзыва (из пользовательского типа постов видео), которые отображаются случайным образом каждый раз при загрузке страницы. Есть разные клиенты, которые оставили отзывы, и в некоторых случаях есть несколько отзывов от одного и того же клиента.
У меня работает запрос, который случайным образом отображает два видео из пользовательского типа постов (при этом полностью исключая одну категорию). Я пытаюсь избежать загрузки двух видеоотзывов от одного и того же клиента (это выглядит странно, если показываются две одинаковые миниатюры), но не уверен, как это сделать. Вот код, который у меня есть на данный момент:
<?php $loop = new WP_Query(array(
'post_type' => 'video',
'posts_per_page' => 2,
'orderby' => 'rand',
'tax_query' => array(
array(
'taxonomy' => 'video_category',
'field' => 'slug',
'terms' => 'assess-core-certification',
'operator' => 'NOT IN')
)
));
?>
<?php if ( $loop ) : while ( $loop->have_posts() ) : $loop->the_post(); ?>
<div class="testimonialVideo top">
<div class="testimonialVideo-video"><?php the_content(); ?></div>
<div class="testimonialVideo-title">
<strong><?php echo get_post_meta( get_the_ID(), 'video_clientName', true ) ?></strong><br/>
<span class="small"><?php echo get_post_meta( get_the_ID(), 'video_clientCompany', true ) ?><br/><br/>
"<em><?php echo get_post_meta( get_the_ID(), 'video_shortQuote', true ) ?></em>"</span>
</div>
</div>
<?php endwhile; else: ?>
<p class="error-not-found">Извините, отзывы не найдены.</p>
<?php endif; wp_reset_postdata();?>
Кажется, вам нужно фактически предотвратить отображение двух конкретных ВИДЕО на одном экране (а не предотвращать отображение видео от одного и того же КЛИЕНТА дважды), но если я ошибаюсь, вы все равно можете адаптировать это. Идея состоит в том, чтобы отправить каждый идентификатор ВИДЕО (имя, id, что угодно) в массив по мере его вывода, проверяя каждый элемент на наличие в массиве, чтобы увидеть, был ли он уже отображен на странице. Если да, пропустите его, если нет – отобразите его и добавьте в список, чтобы избежать повторного отображения.
Вот что я сделал, чтобы избежать дубликатов для случайно отображаемого рекламного плагина, у меня была глобальная переменная, содержащая id изображений, которую я проверял каждый раз, когда выбирался элемент рекламы для случайного отображения.
Другие варианты включают использование meta_query (см. документацию WP_Query в codex) и пользовательский SQL-запрос, оба из которых, по моему мнению, кажутся чрезмерно сложными. Я не уверен, может ли WP_Query возвращать уникальные результаты в наборе метаданных или нет.
Ваш код адаптирован (я не тестировал этот код):
<?php $test_meta_list = array(); // массив для хранения имен элементов, которые были отображены ?>
<?php if ( $loop ) : while ( $loop->have_posts() ) : $loop->the_post();
// Получаем метаданные видео
$test_meta = get_post_meta( get_the_ID(), 'video_clientCompany', true )
// Если оно уже было выведено, пропустите его
if ( in_array($test_meta, $test_meta_list) )
continue();
// Если нет, добавьте его в список и выведите его
else {
array_push($test_meta_list, $test_meta)
?>
<div class="testimonialVideo top">
<div class="testimonialVideo-video"><?php the_content(); ?></div>
<div class="testimonialVideo-title">
<strong><?php echo get_post_meta( get_the_ID(), 'video_clientName', true ) ?></strong><br/>
<span class="small"><?php echo get_post_meta( get_the_ID(), 'video_clientCompany', true ) ?><br/><br/>
"<em><?php echo get_post_meta( get_the_ID(), 'video_shortQuote', true ) ?></em>"
</span>
</div>
</div>
<?php } endwhile; else: ?>
Продолжая тему ответа @Nick. Это сделает так, что запросит ВСЕ видео посты в этой категории, проверяет, равны ли client1 == client2
и если да, показывает пост и увеличивает количество клиентов, которые мы показываем. Цикл должен остановиться после того, как будут показаны 2 поста и выйти.
Идеально, вам бы хотелось запустить SQL-запрос, чтобы сделать это из-за нагрузки, но у меня недостаточно опыта в SQL, так что вы не хотите, чтобы я написал запрос за вас xD
<?php
$loop = new WP_Query(array(
'post_type' => 'video',
'posts_per_page' => -1,
'orderby' => 'rand',
'tax_query' => array(
array(
'taxonomy' => 'video_category',
'field' => 'slug',
'terms' => 'assess-core-certification',
'operator' => 'NOT IN')
)
)
);
?>
<?php
$prevClient="";
$clients = 0;
if ($loop) :
while ($loop->have_posts() && $client < 2) :
$loop->the_post();
$clientUpper = get_post_meta(get_the_ID(), 'video_clientName', true);
$clientLower = strtolower($client);
if ($prevClient != $clientLower) :
$clients++;
$prevClient = $clientLower;
?>
<div class="testimonialVideo top">
<div class="testimonialVideo-video"><?php the_content(); ?></div>
<div class="testimonialVideo-title">
<strong><?php echo clientUpper; ?></strong><br/>
<span class="small"><?php echo get_post_meta(get_the_ID(), 'video_clientCompany', true) ?><br/><br/>
"<em><?php echo get_post_meta(get_the_ID(), 'video_shortQuote', true) ?></em>"</span>
</div>
</div>
<?php endif; endwhile; else: ?>
<p class="error-not-found">Извините, отзывы не найдены.</p>
<?php endif; wp_reset_postdata();?>
Ответ или решение
Использование WP_Query для отображения одного поста из пользовательского типа, учитывая ID в пользовательском поле
Веб-разработка — эта увлекательная область, требующая сосредоточенности на деталях. Ваша задача заключается в правильной настройке WP_Query, чтобы избежать повторного отображения двух видео от одного и того же клиента, что вполне распространенная задача. Давайте разберем, как можно это реализовать.
1. Идея и структура запроса
Ваша текущая задача — случайным образом выбирать два видео из пользовательского типа video
, избегая выбора видео от одного и того же клиента. Мы воспользуемся WP_Query для получения всех необходимых постов, а затем отфильтруем результаты уже в PHP, избегая показов дублей.
2. Создание WP_Query
Вот шаги для реализации вашего запроса:
Шаг 1: Запрос всех необходимых постов
Сначала мы создадим WP_Query для получения всех видео из указанной таксономии, но укажем posts_per_page
равным -1
, чтобы получить все возможные результаты.
$loop = new WP_Query(array(
'post_type' => 'video',
'posts_per_page' => -1,
'orderby' => 'rand',
'tax_query' => array(
array(
'taxonomy' => 'video_category',
'field' => 'slug',
'terms' => 'assess-core-certification',
'operator' => 'NOT IN'
)
)
));
3. Фильтрация постов по клиенту
После того как мы получили все посты, нам необходимо отфильтровать их, чтобы отображать только два поста от разных клиентов. Для этого мы создадим массив для хранения уникальных клиентов.
Шаг 2: Печать постов с уникальными клиентами
Далее мы добавим цикл для вывода видео, проверяя, не был ли этот клиент уже отображен.
$displayed_clients = array(); // Массив для хранения уже отображенных клиентов
$clients_count = 0; // Счётчик клиентов
if ($loop->have_posts()) :
while ($loop->have_posts() && $clients_count < 2) :
$loop->the_post();
// Получаем имя клиента
$client_name = get_post_meta(get_the_ID(), 'video_clientName', true);
// Проверяем, находится ли клиент в массиве ранее отображённых
if (!in_array($client_name, $displayed_clients)) {
// Если нет, добавляем клиента в массив и увеличиваем счётчик
$displayed_clients[] = $client_name;
$clients_count++;
// Выводим содержимое видео
?>
<div class="testimonialVideo top">
<div class="testimonialVideo-video"><?php the_content(); ?></div>
<div class="testimonialVideo-title">
<strong><?php echo esc_html($client_name); ?></strong><br/>
<span class="small">
<?php echo esc_html(get_post_meta(get_the_ID(), 'video_clientCompany', true)); ?><br/><br/>
<em><?php echo esc_html(get_post_meta(get_the_ID(), 'video_shortQuote', true)); ?></em>
</span>
</div>
</div>
<?php
}
endwhile;
else:
echo '<p class="error-not-found">Извините, нет найденныхTestimonials.</p>';
endif;
wp_reset_postdata();
4. Объяснение логики
- Массив
$displayed_clients
: Мы храним в нём имена клиентов, чтобы проверять, был ли клиент уже показан. - Цикл: Мы продолжаем перебор постов до тех пор, пока не достигнем лимита в 2 уникальных клиента. Если клиент уже вывелся, мы просто переходим к следующему посту с помощью
continue
. - Вывод данных: Если клиент ещё не отображался, мы выводим видео и добавляем имя клиента в массив
$displayed_clients
.
Заключение
С помощью описанного выше подхода вы сможете избежать дублирования видео от единственного клиента в вашем контенте, тем самым улучшая пользовательский интерфейс и взаимодействие с пользователями. Этот способ можно легко адаптировать под другие подобные сценарии, делая его универсальным инструментом для управления контентом на WordPress-сайте.