Join the Voxel Guide Community!

Get Involved

You are now eligible to list your profile publicly!

Shortcode to display common words from Timeline

Description/Instructions

This PHP snippet is an adaptation of Miguel’s code that is working for reviews. This one works for post_timeline . 

Adaptation of: https://voxel.guide/snippet/shortcode-to-display-common-words-from-reviews/

It retrieves and analyzes frequently used words and phrases from posts in the post_timeline feed of the Voxel Timeline. It identifies common single words (unigrams) and two-word phrases (bigrams) while filtering out stop words. The results are displayed as a visually styled tag list using the [common_timeline_words limit=”15″] shortcode.

This is useful for highlighting popular topics or keywords from timeline posts. The CSS ensures the tags are neatly arranged in a scrollable row with a soft gradient effect at the edges.

Perfect for showcasing trending discussions or recurring themes in a community-driven WordPress site!

Instructions

Use it in your child theme's functions.php file or code snippet plugin.

if ( ! defined( 'ABSPATH' ) ) {
exit;
}

function voxel_common_timeline_words_shortcode( $atts ) {
global $wpdb, $post;

// Set default shortcode attributes.
$atts = shortcode_atts(
[
'limit' => 10, // Maximum number of phrases to display.
],
$atts,
'common_timeline_words'
);

// Use the provided post_id or fallback to the current post.
$post_id = ! empty( $atts['post_id'] )
? intval( $atts['post_id'] )
: ( isset( $post->ID ) ? $post->ID : 0 );

// Prepare the query to fetch timeline posts from 'post_timeline' feed.
$table_name = $wpdb->prefix . 'voxel_timeline';
$query = $wpdb->prepare(
"SELECT content FROM $table_name WHERE feed = %s",
'post_timeline'
);

if ( $post_id ) {
$query .= $wpdb->prepare(" AND post_id = %d", $post_id);
}

$results = $wpdb->get_results( $query );

// Initialize arrays to store word frequencies.
$unigram_counts = [];
$bigram_counts = [];

// Define an array of common stop words to exclude.
$stop_words = [
'the', 'and', 'a', 'an', 'to', 'of', 'in', 'it', 'is',
'that', 'this', 'i', 'for', 'on', 'with', 'as', 'was',
'but', 'are', 'be', 'by', 'not', 'have', 'had', 'or', 'at',
'from', 'you', 'your', 'they', 'we', 'which'
];

// Process each post content.
foreach ( $results as $result ) {
// Normalize content.
$content = strtolower( strip_tags( $result->content ) );
$content = preg_replace( "/[^\w\s]/", '', $content );
$words = preg_split( '/\s+/', $content, -1, PREG_SPLIT_NO_EMPTY );

// Filter out stop words.
$filtered = array_values( array_filter( $words, function( $word ) use ( $stop_words ) {
return ! in_array( $word, $stop_words, true );
}));

// Get unique unigrams.
$unique_unigrams = array_unique( $filtered );

// Count unigrams.
foreach ( $unique_unigrams as $uni ) {
if ( ! isset( $unigram_counts[ $uni ] ) ) {
$unigram_counts[ $uni ] = 0;
}
$unigram_counts[ $uni ]++;
}

// Generate bigrams.
$bigrams = [];
$count_words = count( $filtered );
for ( $i = 0; $i < $count_words - 1; $i++ ) {
$bigram = $filtered[$i] . ' ' . $filtered[$i + 1];
$bigrams[] = $bigram;
}
$unique_bigrams = array_unique( $bigrams );

// Count bigrams.
foreach ( $unique_bigrams as $bi ) {
if ( ! isset( $bigram_counts[ $bi ] ) ) {
$bigram_counts[ $bi ] = 0;
}
$bigram_counts[ $bi ]++;
}
}

// Remove phrases appearing only once.
$unigram_counts = array_filter( $unigram_counts, function( $count ) {
return $count > 1;
});

$bigram_counts = array_filter( $bigram_counts, function( $count ) {
return $count > 1;
});

// Remove unigrams that appear in selected bigrams.
foreach ( $bigram_counts as $bigram => $bcount ) {
$parts = explode( ' ', $bigram );
foreach ( $parts as $part ) {
if ( isset( $unigram_counts[ $part ] ) ) {
unset( $unigram_counts[ $part ] );
}
}
}

// Merge and sort by frequency.
$merged = array_merge( $unigram_counts, $bigram_counts );
arsort( $merged );

// Limit results.
$merged = array_slice( $merged, 0, intval( $atts['limit'] ), true );

// Build output.
$output = '

';
foreach ( $merged as $phrase => $count ) {
$output .= '' . esc_html( $phrase ) . ' ';
}
$output .= '

';

return $output;
}
add_shortcode( 'common_timeline_words', 'voxel_common_timeline_words_shortcode' );

  • PHP
Copy Code

Instructions

add this to your custom css

.common-timeline-words {
display: flex;
gap: 5px;
overflow-y: auto;
flex-direction: row;
justify-content: flex-start;
align-items: center;
padding-left: 10px;
}

.common-timeline-words span {
font-size: 0.775rem;
padding: 5px 20px;
border-radius: 90px;
border: 1px solid #DEDEDE;
white-space: nowrap;
display: inline-flex;
}

.common-timeline-words:before {
content: '';
position: absolute;
bottom: 0;
left: 0;
background: linear-gradient(to left, transparent, white);
height: 100%;
width: 15px;
}

.common-timeline-words:after {
content: '';
position: absolute;
bottom: 0;
right: 0;
background: linear-gradient(to right, transparent, white);
height: 100%;
width: 20px;
}

  • CSS
Copy Code

Let's Chat About this Snippet

Chat Toggle
Voxel Guide AI
Voxel Guide AI
Voxel Guide AI
Voxel Guide AI
Ask me anything about Voxel!
Send
Powered by AI24