1

I use a custom get_the_excerpt function in my theme. It works perfectly for the first post in the loop, but the other posts are using the standard excerpt function. I do not understand why?

The custom get_the_excerpt function:

function wpse_allowedtags() {
    // Add custom tags to this string
    return '<br>,<b>,<strong>,<em>,<i>,<ul>,<ol>,<li>,<a>,<p>,<h2>,<h3>,<h4>,<h5>'; 
}

remove_filter('get_the_excerpt', 'wp_trim_excerpt');
add_filter('get_the_excerpt', function($wpse_excerpt) {
    $raw_excerpt = $wpse_excerpt;

    if ( '' == $wpse_excerpt ) {
        $wpse_excerpt = get_the_content('');
        $wpse_excerpt = strip_shortcodes( $wpse_excerpt );
        $wpse_excerpt = apply_filters('the_content', $wpse_excerpt);
        $wpse_excerpt = str_replace(']]>', ']]&gt;', $wpse_excerpt);
        $wpse_excerpt = strip_tags($wpse_excerpt, wpse_allowedtags()); 

        $excerpt_word_count = 150;
        $excerpt_length = apply_filters('excerpt_length', $excerpt_word_count); 
        $tokens = array();
        $excerptOutput = '';
        $count = 0;

        // Divide the string into tokens; HTML tags, or words, followed by any whitespace
        preg_match_all('/(<[^>]+>|[^<>\s]+)\s*/u', $wpse_excerpt, $tokens);

        foreach ($tokens[0] as $token) { 
            if ($count >= $excerpt_length && preg_match('/[\,\;\?\.\!]\s*$/uS', $token)) { 
                // Limit reached, continue until , ; ? . or ! occur at the end
                $excerptOutput .= trim($token);
                break;
            }

            // Add words to complete sentence
            $count++;

            // Append what's left of the token
            $excerptOutput .= $token;
        }

        $wpse_excerpt = trim(force_balance_tags($excerptOutput));

        $excerpt_end = '&nbsp;…&nbsp;<a href="'. esc_url( get_permalink() ) . '">' 
                . __('[ weiterlesen ]', 'jankosyk') . '</a>'; 
        $excerpt_more = apply_filters('excerpt_more', ' ' . $excerpt_end); 

        $pos = strrpos($wpse_excerpt, '</');
        if ($pos !== false) {
            // Inside last HTML tag
            $wpse_excerpt = substr_replace($wpse_excerpt, $excerpt_end, $pos, 0); // Add read more next to last word 
        } else {
            // After the content
            $wpse_excerpt .= $excerpt_more; // Add read more in new paragraph 
        }

        return $wpse_excerpt;   

    }
    return apply_filters('wpse_custom_wp_trim_excerpt', $wpse_excerpt, $raw_excerpt);
});

The loop:

<?php if (have_posts()) : while (have_posts()) : the_post(); ?>
    <div class="entry"><?php
        if(is_single() || is_page()) {
            ?><h2><?php the_title(); ?></h2><?php
            the_content();
        } else { ?>
            <h2><a href="<?php the_permalink() ?>"><?php
                the_title(); 
            ?></a></h2><?php
            print get_the_excerpt();
        }  
    ?></div><?php
endwhile; ?>

The website can be found here: https://jankosyk.de/

Any suggestions?

Thanks!


Update:

As I do not use the excerpt from the post edit screen and just want to shorten the post text I ended up with the following function completely ignoring every automatically generated excerpt:

function wpse_allowedtags() {
    // Add custom tags to this string
    return '<br>,<b>,<strong>,<em>,<i>,<ul>,<ol>,<li>,<a>,<p>,<h2>,<h3>,<h4>,<h5>'; 
}
remove_filter('get_the_excerpt', 'wp_trim_excerpt');
add_filter('get_the_excerpt', function() {
    $wpse_excerpt = get_the_content('');
    $wpse_excerpt = strip_shortcodes( $wpse_excerpt );
    $wpse_excerpt = apply_filters('the_content', $wpse_excerpt);
    $wpse_excerpt = str_replace(']]>', ']]&gt;', $wpse_excerpt);
    $wpse_excerpt = strip_tags($wpse_excerpt, wpse_allowedtags()); 

    $excerpt_word_count = 150;
    $excerpt_length = apply_filters('excerpt_length', $excerpt_word_count); 
    $tokens = array();
    $excerptOutput = '';
    $count = 0;

    // Divide the string into tokens; HTML tags, or words, followed by any whitespace
    preg_match_all('/(<[^>]+>|[^<>\s]+)\s*/u', $wpse_excerpt, $tokens);

    foreach ($tokens[0] as $token) { 
        if ($count >= $excerpt_length && preg_match('/[\,\;\?\.\!]\s*$/uS', $token)) { 
            // Limit reached, continue until , ; ? . or ! occur at the end
            $excerptOutput .= trim($token);
            break;
        }

        // Add words to complete sentence
        $count++;

        // Append what's left of the token
        $excerptOutput .= $token;
    }

    $wpse_excerpt = trim(force_balance_tags($excerptOutput));

    $excerpt_end = '&nbsp;…&nbsp;<a href="'. esc_url( get_permalink() ) . '">' 
            . __('[ weiterlesen ]', 'jankosyk') . '</a>'; 
    $excerpt_more = apply_filters('excerpt_more', ' ' . $excerpt_end); 

    $pos = strrpos($wpse_excerpt, '</');
    if ($pos !== false) {
        // Inside last HTML tag
        $wpse_excerpt = substr_replace($wpse_excerpt, $excerpt_end, $pos, 0); // Add read more next to last word 
    } else {
        // After the content
        $wpse_excerpt .= $excerpt_more; // Add read more in new paragraph 
    }

    return $wpse_excerpt;   
});

1 Answer 1

0

One possibility would be to simply write your custom filter to run later than the default priority of "10" (which is what the "wp_trim_excerpt" function is running at).

The get_the_excerpt filter passes the excerpt AND the post object. So you should be able to run your filter at a later priority and use the excerpt value from the post object instead of the passed excerpt, since that has already gone through another filter.

I changed your original from the anonymous function as you had it just for clarity on the priority and argument values.

// Running this filter at priority 20 so it comes later than wp_trim_excerpt()
add_filter( 'get_the_excerpt', 'my_later_excerpt', 20, 2 );
function my_later_excerpt( $possibly_filtered_excerpt , $post_obj ) {

    /*
     * Rather than change every instance of $wpse_excerpt in your
     * function, I changed the argument to $possibly_filtered_excerpt
     * and ignored it. Then set the $wpse_excerpt value to the 
     * excerpt contained in the post object ($post_obj->post_excerpt)
     */
    $wpse_excerpt = $post_obj->post_excerpt;

    $raw_excerpt = $wpse_excerpt;

    if ( '' == $wpse_excerpt ) {
        $wpse_excerpt = get_the_content('');
        $wpse_excerpt = strip_shortcodes( $wpse_excerpt );
        $wpse_excerpt = apply_filters('the_content', $wpse_excerpt);
        $wpse_excerpt = str_replace(']]>', ']]&gt;', $wpse_excerpt);
        $wpse_excerpt = strip_tags($wpse_excerpt, wpse_allowedtags()); 

        $excerpt_word_count = 150;
        $excerpt_length = apply_filters('excerpt_length', $excerpt_word_count); 
        $tokens = array();
        $excerptOutput = '';
        $count = 0;

        // Divide the string into tokens; HTML tags, or words, followed by any whitespace
        preg_match_all('/(<[^>]+>|[^<>\s]+)\s*/u', $wpse_excerpt, $tokens);

        foreach ($tokens[0] as $token) { 
            if ($count >= $excerpt_length && preg_match('/[\,\;\?\.\!]\s*$/uS', $token)) { 
                // Limit reached, continue until , ; ? . or ! occur at the end
                $excerptOutput .= trim($token);
                break;
            }

            // Add words to complete sentence
            $count++;

            // Append what's left of the token
            $excerptOutput .= $token;
        }

        $wpse_excerpt = trim(force_balance_tags($excerptOutput));

        $excerpt_end = '&nbsp;…&nbsp;<a href="'. esc_url( get_permalink() ) . '">' 
                . __('[ weiterlesen ]', 'jankosyk') . '</a>'; 
        $excerpt_more = apply_filters('excerpt_more', ' ' . $excerpt_end); 

        $pos = strrpos($wpse_excerpt, '</');
        if ($pos !== false) {
            // Inside last HTML tag
            $wpse_excerpt = substr_replace($wpse_excerpt, $excerpt_end, $pos, 0); // Add read more next to last word 
        } else {
            // After the content
            $wpse_excerpt .= $excerpt_more; // Add read more in new paragraph 
        }

        return $wpse_excerpt;   

    }
    return apply_filters('wpse_custom_wp_trim_excerpt', $wpse_excerpt, $raw_excerpt);
}
3
  • I had to change the line $wpse_excerpt = $post_ojb->post_excerpt; in two ways: First the typo in $post_obj and second I had to use post_text as the post_excerpt was already filtered. In this way it maybe ignore the excerpts from the post edit screen, but I do not use them.
    – g4rf
    Oct 10, 2018 at 16:21
  • I altered the function ignoring every automatically generated excerpts, see the original post.
    – g4rf
    Oct 10, 2018 at 16:35
  • Whoops! Sorry about the typo :-( I must have been going too fast.
    – butlerblog
    Oct 11, 2018 at 13:37

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.