Display Posts Group by Alphabets in WordPress

Advertisement

Create an array of posts group by alphabet with WP_Query.

Use below to create the list of posts array with the group by alphabet.

Note: I have used post type. You can change this post type with your own. Also, you can modify the WP_Query parameters.

<?php
/**
* Get posts group by alphabets.
*
* @todo Change the `prefix_` and with your own unique prefix.
*
* @since 1.0.0
*/
if( ! function_exists( 'prefix_get_posts_group_by_alphabet' ) ) :
function prefix_get_posts_group_by_alphabet() {
$result = array();
$query_args = array(
'post_type' => 'post',
// Query performance optimization.
'no_found_rows' => true,
'posts_per_page' => 100,
);
$query = new WP_Query( $query_args );
if ( $query->posts ) {
foreach ( $query->posts as $key => $post ) {
$first_letter = substr($post->post_title,0,1);
if( ! empty( $first_letter ) ) {
$result[$first_letter][] = array(
'ID' => $post->ID,
'title' => $post->post_title,
);
}
}
}
if( ! empty( $result ) ) {
ksort( $result );
}
return $result;
}
endif;

Now we can show the posts with the group by alphabet with a shortcode.

In below code we have created a shortcode prefix_alphabetic_posts to show the result in the post.

NOTE: Below short code is created only for demo purpose. So, Added inline CSS. You need to use wp_enqueue_scripts to enqueue your scripts.

<?php
add_shortcode( 'prefix_alphabetic_posts', 'prefix_alphabetic_posts' );
function prefix_alphabetic_posts() {
ob_start();
?>
<style type="text/css">
#alphabetical-posts .letters li {
display: inline-block;
margin: 0;
}
#alphabetical-posts .letters a {
text-decoration: none;
font-size: 16px;
background: #ffffff;
height: 2em;
display: inline-block;
width: 2em;
line-height: 2em;
color: #2196F3;
margin: 0;
}
#alphabetical-posts .letters {
text-align: center;
display: inline-flex;
}
#alphabetical-posts .letters-wrap {
text-align: center;
}
#alphabetical-posts .letters a:hover {
background: #2196F3;
color: #fff;
}
#alphabetical-posts .posts {
margin-top: 4em;
max-width: 900px;
margin: 0 auto;
}
#alphabetical-posts .posts .item {
margin-bottom: 4em;
}
#alphabetical-posts .posts .item a {
text-decoration: none;
font-size: 14px;
}
#alphabetical-posts .posts .list > div {
background: #fff;
padding: 15px 15px;
border-bottom: 1px solid #f2f2f2;
}
#alphabetical-posts .list h3 {
margin: 0;
}
#alphabetical-posts .list .content {
margin-top: 5px;
}
</style>
<?php
$result = prefix_get_posts_group_by_alphabet();
if( $result ) { ?>
<div id="alphabetical-posts">
<?php $letters = array_keys($result); ?>
<?php if( $letters ) { ?>
<div class="letters-wrap">
<ul class="letters">
<?php foreach( $letters as $key => $letter ) { ?>
<li><a href="#goto-letter-<?php echo $letter; ?>"><?php echo $letter; ?></a></li>
<?php } ?>
</ul>
</div>
<?php } ?>
<div class="posts">
<?php foreach( $result as $letter => $posts ) { ?>
<div id="goto-letter-<?php echo $letter; ?>" class="item">
<h3><?php echo $letter; ?></h3>
<div class="list">
<?php foreach( $posts as $key => $post ) { ?>
<div>
<h3><a href="#"><?php echo $post['title']; ?></a></h3>
<div class="content">
<?php echo wp_trim_words( get_the_excerpt( $post['ID'] ), 20 ); ?>
</div>
</div>
<?php } ?>
</div>
</div>
<?php } ?>
</div>
</div>
<?php }
return ob_get_clean();
}

Leave a Reply