ACF Repeater random order all fields - php

Looking to output a Advanced Custom Fields repeater in random order. I have a repeater field "profiles" containing 5 "profile" post objects.
My code today is:
// Randomize and shuffle the rows
$rows = get_sub_field('profiles');
shuffle($rows);
$rand_repeater_fields = array_rand( $rows , 4 ); ?>
<?php if( have_rows('profiles') ):
$stage_index = 0; ?>
<?php while ( have_rows('profiles') ) : the_row();
// print rows only if in array
if (in_array(get_row_index() - 1, $rand_repeater_fields)) { ?>
<?php $post_object = get_sub_field('profile'); //row w. post object start
if( $post_object ):
$post = $post_object;
setup_postdata( $post ); ?>
<?php the_permalink();?>
<?php wp_reset_postdata(); ?>
<?php endif; ?> //row w. post object end
<?php // increment index
$stage_index++;
} ?>
<?php endwhile; ?>
This code successfully output 4 of 5 rows in random order, which means that it almost works as I wish.
How do I update this snippet to output ALL fields of the repeater fields, in random order, even if they are 3 or 10 in total?
Thankful for any suggestions!

<?php
$args = array(
'post_type' => 'page',
'post_status' => 'publish',
'posts_per_page' => -1,
'orderby' => 'rand',
'meta_query' => array(
array(
'key' => 'profiles',
'compare' => 'EXISTS'
)
)
);
$query = new WP_Query( $args );
if ( $query->have_posts() ) {
while ( $query->have_posts() ) {
$query->the_post();
$profiles = get_field('profiles');
if( $profiles ):
foreach( $profiles as $profile ):
echo '<div class="profile">';
echo '<h2>' . $profile['profile'] . '</h2>';
echo '</div>';
endforeach;
endif;
}
}
wp_reset_postdata();
?>

Related

How to insert a custom code between the posts inside the Wordpress loop?

Right now I have a very basic Wordpress loop:
<?php
// get posts
$posts = get_posts(array(
'post_type' => 'page',
'posts_per_page' => 30,
'order' => 'DESC'
));
if( $posts ): ?>
<?php foreach( $posts as $post ):
setup_postdata( $post )
?>
<?php the_title(); ?>
<?php endforeach; ?>
<?php wp_reset_postdata(); ?>
<?php endif; ?>
Basically I'm trying to insert an ad between the posts.
And have an option to specify after how many posts the ad code would appear.
So if I type 3, then it would look like this:
Post 1 title
Post 2 title
Post 3 title
AD
Post 4 title
Post 5 title
Post 6 title
AD
...
In the other similar thread I have found that I can do that using a counter:
$i = 1;
if($i==3||$i==5||$i==10){
/*Adsence here*/
}
$i++;
But I have no idea how to implement that into my code.
Not a coder, just trying to combine something.
Thanks.
You can initialize a counter, set it to zero and add one to it after every loop. You can then check for the current value of the counter and do things when it reaches a certain value.
<?php
// get posts
$posts = get_posts(array(
'post_type' => 'page',
'posts_per_page' => 30,
'order' => 'DESC'
));
$counter = 0;
if( $posts ): ?>
<?php foreach( $posts as $post ):
setup_postdata( $post )
?>
<?php the_title(); ?>
<?php
// checks if $counter exists in the array
if (in_array($counter, array(3, 6, 9))) {
// do something when $counter is equal to 3, 6, or 9
// such as rendering an ad
}
$counter++;
?>
<?php endforeach; ?>
<?php wp_reset_postdata(); ?>
<?php endif; ?>
You could set this up in multiple ways. For example you could use current_post inside the loop to get the current loop index:
$posts = new wp_query(
array(
'post_type' => 'page',
'posts_per_page' => 30,
'order' => 'DESC'
)
);
if( $posts ):
while($posts->have_posts())
{
$posts->the_post();
$current_post = $posts->current_post; // starts from zero
if($current_post == 2 || $current_post == 4 || $current_post == 9):?>
<div>YOUR ADSENCE</div>
<?php
endif;
?>
<h3><?php the_title(); ?></h3>
<?php
}
endif;
Or if you want to use a counter, then you could do something like this:
$posts = new wp_query(
array(
'post_type' => 'page',
'posts_per_page' => 30,
'order' => 'DESC'
)
);
if( $posts ):
$i = 1; // starts from one OR you could change it to zero to starts from zero if you want to
while($posts->have_posts())
{
$posts->the_post();
if($i == 3 || $i == 5 || $i == 10):?>
<div>YOUR ADSENCE</div>
<?php
endif;
?>
<h3><?php the_title(); ?></h3>
<?php
$i++;
}
endif;

Display html for selected products or products categories

Hello I am using advanced custom field plugin for displaying some html only for selected products or only for products for selected categories in option page with relationship picker. My result instead is displaying for all products. This is what I have:
$products = get_field('products_picker', 'option');
$categories = get_field('categories_picker', 'option');
$prom_img = get_field('prom_img', 'option');
if ( $products ) {
foreach( $products as $p ):
if( $post->ID == $p->ID ):
<img src="<?php echo $prom_img['url']; ?>">
endif;
endforeach;
}
if ( $categories ) {
foreach( $categories as $term ):
$category = get_term( $term );
if( has_term( $category, 'product_cat', $post )) {
?>
<img src="<?php echo $prom_img['url']; ?>">
endif;
endforeach;
}
In similar cases I create a new wp_query passing the array with the post IDs like below:
$posts = get_field('products_picker', 'option');
$new_query = new WP_Query(array(
'post_type' => array('post'),
'post__in' => $posts,
'orderby' => 'post__in',
));
if ( $new_query->have_posts() ) :
while ( $new_query->have_posts() ) : $new_query->the_post();
//your code here
endwhile;
endif;
For the categories part you can use a query like this:
$categories = get_field('categories_picker', 'option');
$args = array(
'post_type' => 'post',
'tax_query' => array(
array(
'taxonomy' => 'category',
'field' => 'term_id',
'terms' => $categories[0]
)
)
);
$cat_query = new WP_Query($args);
I've not tested this in Wordpress, but the first thing I would try is to rename the $post variable that pulls the ACF field to '$posts' (plural).
Then change the foreach loop as follows.
$posts = get_field('products_picker', 'option');
$prom_img = get_field('prom_img', 'option');
if ( $posts ) {
foreach( $posts as $post ):
setup_postdata($post);
$sales_html = '<div class="promo-badge test"><img src=' . $prom_img['url'] . '></div>';
wp_reset_postdata();
endforeach;
}
That might fix it... I'm not sure you won't need to turn the foreach loop into an actual Wordpress style loop (the type with while(have_posts()): the_post(); etc. like in #kaize answer below)
See here if my solution didn't help: https://www.advancedcustomfields.com/resources/querying-relationship-fields/

Wordpress - Exclude posts from author from wp_query

I'm trying to exclude posts by the author with the ID "1" form WP_Query. This still shows all posts by all users.
Any thoughts?
<?php
$temp = $wp_query;
$wp_query= null;
$wp_query = new WP_Query( array( 'author' => -1 ) );
$wp_query->query('posts_per_page=35'.'&paged='.$paged);
while ($wp_query->have_posts()) : $wp_query->the_post();
?>
<div class="grid__third">
...
</div>
<?php endwhile; // end of loop
?>
Thanks a lot!
try this
global $post;
$args=array('author' => '-1', //excludes users with id 1.
'post_type' => 'post',
'post_status' => 'publish',
'posts_per_page' => 12,
'ignore_sticky_posts'=> 1,);
$myposts = get_posts( $args );
foreach ( $myposts as $post ) : setup_postdata( $post ); ?>
<li>
<?php the_title(); ?>
</li>
<?php endforeach;
wp_reset_postdata();?>
or
// The Query
$args=array('author' => '-1', //excludes users with id 1.
'post_type' => 'post','post_status' => 'publish','posts_per_page' => 12,'ignore_sticky_posts'=> 1,);
$the_query = new WP_Query( $args ); // The Loop
if ( $the_query->have_posts() ) {
echo '<ul>';
while ( $the_query->have_posts() ) {
$the_query->the_post();
echo '<li>' . get_the_title() . '</li>';
}
echo '</ul>';
/* Restore original Post Data */
wp_reset_postdata();}else {
// no posts found
}
If your query is not working with
$wp_query = new WP_Query( array( 'author' => -1 ) );
then, You can try some other logic. Like inside the loop get the ID of the author by using POST ID:
$post_author_id = get_post_field( 'post_author', $post_id ); // You will get your author id here
Then apply condition like if($post_author_id != 1){ // YOUR POST } This will display post of all author except author with ID = 1.
Full code like:
while ($wp_query->have_posts()) : $wp_query->the_post();
$post_author_id = get_post_field( 'post_author', HERE YOUR POST ID );
if($post_author_id != 1){
?>
<div class="grid__third">
...
</div>
<?php
} endwhile; // end of loop
Hope this will helpful for you. Thanks.

WordPress (nested) Post query, loop per category and then per ACF

I'll first tell my goal, than what I came up with so far.
My goal:
I've made a shortcode that works with VisualComposer.
In VC I can check the categories for this posttype.
The goal of the short code is to fist select and sort the posts per selected category.
Second, to divide and sort per ACF. Say, "custom_field_1"
Thirdly and last. to sort the posts alphabetically on "custom_field_2" and then on "custom_field_3".
Example:
Cat 1
red
post 1
post 2
blue
post 3
post 4
Cat 2
red
post 5
post 6
blue
post 7
post 8
Al right. I've tried it out myself first. And this is my code so far:
<?php
function productlist_sc($atts){?>
<?php
global $post;
$categories_array = array();
$thecategories = get_categories();
foreach( $thecategories as $category ){
$categories_array[] = $category->slug;
}
if($atts[ 'category' ]){
$atts[ 'category' ] = explode( ",", $atts[ 'category' ] );
}
//collect values, combining passed in values and defaults
$values = shortcode_atts(array(
'category' => ''
),$atts);
$categories = get_categories( array(
'orderby' => 'name',
'parent' => 0,
'slug' => $values['category']
) );
$current = get_the_ID($post->ID);
$cargs = array(
//'child_of' => 0,
'orderby' => 'name',
'parent' => 0,
'order' => 'ASC',
'hide_empty' => 1
//'taxonomy' => 'category', //change this to any taxonomy
);
// first sort all selected posts per category
foreach ( $categories as $tax ) :
// List posts by the terms for a custom taxonomy of any post type
$args = array(
'post_type' => 'products',
'orderby' => 'ASC',
'posts_per_page'=>-1,
'category_name' => $tax->slug
);
$the_query = new WP_Query( $args ); ?>
<?php if ( $the_query->have_posts() ) : ?>
<h2>Internal ID: <?php echo $tax->name; ?></h2><?php
// second sort all selected posts per custom_field_1
$mykey_values = get_post_custom_values( 'custom_field_1' );
foreach ( $mykey_values as $key => $value ) :
?><h3><?php the_field('custom_field_1'); ?></h3>
<div class="rtt_prod_table">
<!-- the loop -->
<?php while ( $the_query->have_posts() ) : $the_query->the_post(); ?>
<div>
<?php if( get_field('custom_field_1') || get_field('custom_field_2') || get_field('custom_field_3') ): ?>
<ul>
<?php if( get_field('custom_field_2') ): ?>
<li>
<?php the_field('custom_field_2'); ?>
</li>
<?php endif; ?>
<?php if( get_field('custom_field_3') ): ?>
<li>
<?php the_field('custom_field_3'); ?>
</li>
<?php endif; ?>
</ul>
<?php endif; ?>
</div>
</div>
</div>
<?php endwhile; ?> <!-- end of the loop -->
<div><!-- end .accord-content -->
</div>
<?php wp_reset_postdata();
endforeach; // custom_field_1
?>
<?php else : ?>
<p><?php _e( 'Sorry, no posts matched your criteria.' ); ?></p>
<?php endif; ?>
<?php
endforeach; /* end $tax */ ?>
<?php
}
Alright, so I've found the answer.
I'll post it here for anyone looking for a solution. :)
Steps:
needed an array with all the unique values within "field 1"
ran an post query for each post, grabbed the value of "field 1" and put in an array
filtered all the duplicates
alphabetized the array
run a foreach in the array:
This is the code I added to the code above
$stack = array();
// query
$args = array(
'post_type' => 'products',
'orderby' => 'ASC',
'posts_per_page'=>-1,
'category_name' => $tax->slug
);
// The Query
$the_query = new WP_Query( $args );
// The Loop
if ( $the_query->have_posts() ) {
while ( $the_query->have_posts() ) {
$the_query->the_post();
if( get_field('custom_field_1') ):
$stack[] = get_field('custom_field_1');
endif;
}
wp_reset_postdata();
}
$result = array_unique($stack);
sort($result);
foreach ( $result as $tax2 ) :
// run you code here
endforeach;
Have a great day boys and girls!

Get all terms in a custom Wordpress Query?

I know how to get all of the Wordpress terms, but I need a "filtered" down version of the results. Is it possible to get all of the terms that are in the result of a Wordpress query? I have this query here:
<?php
$args=array(
'post_type' => 'gw_activity',
'post_status' => 'publish',
'orderby' => 'date',
'meta_query' => array(
'relation' => 'AND',
array(
'key' => 'activity_category',
'value' => 'mindful_life',
'compare' => '='
)
),
'posts_per_page' => 10
);
$my_query = null;
$my_query = new WP_Query($args);
if( $my_query->have_posts() ) {
$all_terms = array();
while ($my_query->have_posts()) : $my_query->the_post(); ?>
<?php $terms = wp_get_post_terms( $my_query->post->ID, array( 'gw_activity_tag' ) ); ?>
<?php
foreach ( $terms as $term ) {
$all_terms[] = $term->name;
}
?>
<?php endwhile; }
wp_reset_query();
?>
<!-- End Custom Query -->
<?php
$unique_terms = array_unique( $all_terms );
$result = array_unique($unique_terms);
foreach ($result as $value) {
echo $value . '<br />';
}
?>
But I can't figure how to run the query & put a "Where" clause in it, like you can with MySQL. Any help / suggestion or even point me in the right direction would be greatly appreciated. I'm stuck
Check this function: wp_get_post_terms()
Assuming your post supports two taxonomies called tax_a and tax_b, you can try something like this, exactly where you wrote your comment:
<?php $terms = wp_get_post_terms( $query->post->ID, array( 'tax_a', 'tax_b' ) ); ?>
<?php foreach ( $terms as $term ) : ?>
<p><?php echo $term->taxonomy; ?>: <?php echo $term->name; ?></p>
<?php endforeach; ?>
This will print all the terms for each post retrieved by the query.
EDIT
If what you want is all the terms in all the posts retrieved by the query, you can store the values in an array and then use a function like array_unique(), like this:
$all_terms = array();
foreach ( $terms as $term ) {
$all_terms[] = $term->name;
}
// ... and outside the WHILE loop
$result = array_unique( $all_terms );
foreach ( $result as $term ) {
echo $term . '<br/>;
}

Categories