【问题标题】:How to group Wordpress posts in years and then months?如何在几年和几个月内对 Wordpress 帖子进行分组?
【发布时间】:2021-08-24 15:47:10
【问题描述】:

我正在尝试使用后查询和输出中的以下结构创建一个函数:

2021 一月 1.帖子标题 2.帖子标题 行进 3.帖子标题 2020 可能 4.帖子标题

这是我到目前为止所做的:

global $post;

$posts = get_posts( array(
    'post_type' => 'history',
    'orderby'   => 'date'
) );

$_year_mon = '';
$_has_grp = false;

foreach ( $posts as $post ) {
    setup_postdata( $post );

    $time = strtotime( $post->post_date );
    $year = date( 'Y', $time );
    $mon = date( 'F', $time );
    $year_mon = "$year-$mon";

    if ( $year_mon !== $_year_mon ) {
        // Close previous group, if any.
        if ( $_has_grp ) {
            echo '</div>';
            echo '</div>';
        }
        $_has_grp = true;

        echo '<div class="year">';
        echo "<span>$year</span>";

        echo '<div class="month">';
        echo "<span>$mon</span>";
    }

    // Display post title.
    if ( $title = get_the_title() ) {
        echo "<div>$title</div>";
    } else {
        echo "<div>#{$post->ID}</div>";
    }

    $_year_mon = $year_mon;
}

if ( $_has_grp ) {
    echo '</div>';
    echo '</div>';
}

wp_reset_postdata();

问题是具有多个月份的同一年没有分组在一个元素中..

当前输出:

2021 一月 1.帖子标题 2.帖子标题 2021 行进 3.帖子标题 2020 可能 4.帖子标题

【问题讨论】:

    标签: php wordpress multidimensional-array wordpress-theming custom-wordpress-pages


    【解决方案1】:

    以下解决方案已经过全面测试,并且对于默认的 wordpress post 类型可以无缝运行。如果您想为具有自己的自定义字段的自定义帖子类型运行它,那么您可能会遇到一些差异。因此,请随时根据需要为您自己的自定义帖子类型进行自定义。

    正如我们在this question 上讨论的那样,当您使用get_posts 时,它将返回post objects。每个post object 包含以下属性/数据:

    WP_Post Object
    (
        [ID] =>
        [post_author] =>
        [post_date] => 
        [post_date_gmt] => 
        [post_content] => 
        [post_title] => 
        [post_excerpt] => 
        [post_status] =>
        [comment_status] =>
        [ping_status] => 
        [post_password] => 
        [post_name] =>
        [to_ping] => 
        [pinged] => 
        [post_modified] => 
        [post_modified_gmt] =>
        [post_content_filtered] => 
        [post_parent] => 
        [guid] => 
        [menu_order] =>
        [post_type] =>
        [post_mime_type] => 
        [comment_count] =>
        [filter] =>
    )
    

    例如,如果您需要帖子的titlecontentauthorexerpt,那么您可以创建一个多维数组并使用array_push 函数来创建您的自定义数组,如下所示:

    $posts = get_posts(array(
      'post_type' => 'history', // Since 'history' is a custom post type, I tested it on 'post'
    //'post_type' => 'post'
      'posts_per_page' => -1,
      'orderby'   => 'date'
    ));
    
    // You could see the number of posts for your query
    echo "Number of posts found: ". count($posts) . "<br>";
    
    $your_custom_array_yearly = array();
    
    foreach ($posts as $post) {
      setup_postdata($post);
      $time = strtotime($post->post_date);
      $year = date('Y', $time);
      $mon = date('F', $time);
    
      if (!($your_custom_array_yearly[$year][$mon])) {
        $your_custom_array_yearly[$year][$mon] = array();
        array_push(
          $your_custom_array_yearly[$year][$mon],
          [
            'title'   => $post->post_title,
            'excerpt' => $post->post_excerpt,
            'author'  => $post->post_author,
            'content' => $post->post_content,
          ]
        );
      } else {
        array_push(
          $your_custom_array_yearly[$year][$mon],
          [
            'title'   => $post->post_title,
            'excerpt' => $post->post_excerpt,
            'author'  => $post->post_author,
            'content' => $post->post_content,
          ]
        );
      };
    }
    
    wp_reset_postdata();
    

    为了调试/调查数组,你可以使用这个:

    echo "<pre>";
    print_r($your_custom_array_yearly);
    echo "</pre>";
    

    既然您有自己的自定义数组,那么您可以循环遍历它并输出您的数据:

    foreach ((array)$your_custom_array_yearly as $yearly => $yvalue) {
      echo $yearly . ": <br>";
      echo "<ul>";
      foreach ($yvalue as $monthly => $mvalue) {
        echo "<li>" . $monthly . ": </li><ul>";
        foreach ($mvalue as $monthly_k => $monthly_v) {
          foreach ($monthly_v as $post_title_k => $post_title_v) {
            echo "<li>" . $post_title_k . ": " . $post_title_v . "</li></ul>";
          }
        }
      }
      echo "</ul>";
    }
    

    以上代码会输出如下结果:

    2021:
      January:
        1.Title: Post Title
        1.Excerpt: Post excerpt
        1.Author: Post author
        1.Content: Post content
        2.Title: Post Title
        2.Excerpt: Post excerpt
        2.Author: Post author
        2.Content: Post content
      March:
        3.Title: Post Title
        3.Excerpt: Post excerpt
        3.Author: Post author
        3.Content: Post content
    
    2020:
      May:
        4.Title: Post Title
        4.Excerpt: Post excerpt
        4.Author: Post author
        4.Content: Post content
    

    【讨论】:

    • 非常感谢您的解释!与第 4 级 foreach 有点混淆,在我的实现中,我得到:foreach ($month_value as $monthly_k =&gt; $monthly_v) { $output_inner .= '&lt;div class="visible"&gt;'; foreach ($monthly_v as $post_title_k =&gt; $post_title_v) { $output_inner .= '&lt;div&gt;&lt;h3&gt;'. $post_title_k .'&lt;/h3&gt;'. $post_title_v .'&lt;/div&gt;'; } $output_inner .= '&lt;/div&gt;'; } } 输出:&lt;div class="visible"&gt;&lt;div&gt;&lt;h3&gt;title&lt;/h3&gt;Lorem ipsum dolor sit amet [cloned]&lt;/div&gt;&lt;div&gt;&lt;h3&gt;content&lt;/h3&gt;&lt;!-- content --&gt;&lt;/div&gt;&lt;/div&gt; h3 标签中不需要的标题,包装可能有问题。
    • 好吧,我昨天在我的一个博客上对其进行了测试,它运行良好!唯一的区别是我使用了'post_type' =&gt; 'post' 而不是'post_type' =&gt; 'history',这是我相信你已经想出的自定义帖子类型,这将我们带到了它的html结构!您最终看到的 html 结构将来自您的 titleexcerptcontent 和您的自定义帖子类型 historyauthor。默认情况下,我的 foreach 循环不输出 h3s 或 divs 等。我的 foreach 只有一个简单的 ulli 标签,你看到的任何额外的 html 标签/结构都来自你的结束。
    • 我明白了.. 顺便说一句,仅通过使用 $monthly_v[$post_title_v] 设法获取值,但是在包装标签时,例如$output_inner .= '&lt;h3&gt;' . $monthly_v[$post_title_v] . '&lt;/h3&gt;'; 例如,标签出现在输出中的字符串之外。我会更深入地调查它,谢谢!!!
    • 要调试/调查代码,您可以在contenttitleexcerpt 中创建一些没有任何 html 标记的“虚拟”历史帖子。然后运行代码并查看您刚刚为调试目的创建的简单虚拟数据的结果,然后您将了解发生了什么。就像我说的那样,它在默认的 wordpress post 上工作OK。昨天在我发给你之前测试过了。
    • 想通了!那个适用于我的情况:foreach ($month_value as $monthly_k =&gt; $monthly_v) { $output_inner .= '&lt;div class="visible"&gt;'; $output_inner .= '&lt;h3&gt;'; foreach ($monthly_v as $content_key =&gt; $content_value) { $output_inner .= $content_value; $output_inner .= '&lt;/h3&gt;'; } $output_inner .= '&lt;/div&gt;'; } 想给你买杯咖啡,但取消了我的 PayPal 订阅,你有其他钱包吗? =)
    【解决方案2】:

    像这样创建一个多维数组并打印出来。您可能会得到适当的结果。

    $master = [];
    
    foreach ( $posts as $post ) {
        setup_postdata( $post );
    
        $time = strtotime( $post->post_date );
        $year = date( 'Y', $time );
        $mon = date( 'F', $time );
        
        $master[$year][$mon][] = $post;
    }
    
    wp_reset_postdata();
    
    echo '<pre>';
    print_r($master);
    echo '</pre>';
    

    【讨论】:

    • 不错的解决方案!尝试以这种方式迭代数组:foreach ($master as $masterkey =&gt; $mastervalue) { echo "&lt;p&gt;"; echo "masterkey: ". $masterkey . "&lt;br&gt;"; foreach($mastervalue as $key =&gt; $value) { echo "key: " . $key . "&lt;br&gt;"; echo "value: " . $value . "&lt;br&gt;"; } echo "&lt;/p&gt;"; } How I can get post data form $value array?
    • 找到解决方案:$value['content'] = get_the_content()
    • 您将在 $value 中获取整个帖子对象,因此在循环中再次设置帖子数据,您可以访问内置函数,如 get_permalink()、get_title()、get_the_content() 等
    猜你喜欢
    • 2019-09-13
    • 1970-01-01
    • 1970-01-01
    • 2020-07-22
    • 1970-01-01
    • 2016-11-17
    • 2021-06-28
    • 2016-11-04
    • 1970-01-01
    相关资源
    最近更新 更多