String"返回"功能被打破了,但是" echo"作品

时间:2016-12-09 16:26:57

标签: php wordpress

我正在制作我的第一个Wordpress插件,它非常有趣。

我使用echo来显示HTML,但它显示在页面顶部。做一些挖掘,我发现我应该使用" return"在功能中。切换到"返回"导致其他问题。看起来我尝试输出的字符串()正被"返回"破坏。我可以使用echo输出字符串,它可以工作(只是在错误的地方)。

有什么想法吗?

function v3grid_func($atts) {

// Get the parameters from the shortcode
$atts = shortcode_atts(

    array(
        'count' => 3,
        'link_to_all' => 'yes',
        'css_class' => 'v3grid',
        'categories' => '1'
    ), $atts

);

// Get list of recent posts
$args = array(
    'numberposts' => $atts['count'],
    'offset' => 0,
    'category' => 0,
    'orderby' => 'post_date',
    'order' => 'DESC',
    'include' => '',
    'exclude' => '',
    'meta_key' => '',
    'meta_value' =>'',
    //'post_type' => array('post', 'podcast', 'recipe', 'roundup'),
    'post_type' => array('roundup'),
    'post_status' => 'publish',
    'suppress_filters' => true
);

$recent_posts = wp_get_recent_posts( $args, ARRAY_A );

// Figure out width requirement for each grid item
$width = 100/$atts[count];

$output = '';

// Container for row start
$output .=  'Start -> <div style="margin:0 -10px 0 -10px; box-sizing: border-box; position:relative; display:block;">';

// Loop through posts
foreach( $recent_posts as $recent ){

        // Get the URL of the feature image for the post
        $thumbnail = htmlentities(get_the_post_thumbnail_url( $recent["ID"], 'full' ));

        $url = htmlentities(get_permalink($recent["ID"]));
        $title = htmlentities($recent["post_title"]);

        $output .=  '   1 - <div style="width:'.$width.'%; float:left; padding:10px; display:block;">';
        $output .=  '       2 - <div><img src="'.$thumbnail.'" style="display:block; width:100%;"></div>'; // <-- Problem likely here           
        $output .=  '       3 - <div><a href="'.$url.'">'.$title.'</a></div>';
        $output .=  '   4 - </div>';

    }

// Container for row end
$output .=  'End -> </div>';

echo $output; // Shows everything as expected
return $output; // Does not show everything as expected (need to use return)

wp_reset_query();

}

add_shortcode('v3grid', 'v3grid_func');

这是echo和return的输出。我添加了开始,结束和数字,所以我可以跟踪输出。认为这是我的foreach中的一个问题。

输出使用&#34; echo&#34;在功能 - 输出是好的。

Start -> <div style="margin:0 -10px 0 -10px; box-sizing: border-box; position:relative; display:block;">    

1 - <div style="width:25%; float:left; padding:10px; display:block;">       
2 - <div><img src="/wp-content/uploads/THUMBNAIL-150x150.jpg" style="display:block; width:100%;"></div>     
3 - <div><a href="/roundup/post1/">Post Title A</a></div>   
4 - </div>  

1 - <div style="width:25%; float:left; padding:10px; display:block;">       
2 - <div><img src="/wp-content/uploads/THUMBNAIL-1-150x150.jpg" style="display:block; width:100%;"></div>       
3 - <div><a href="/roundup/post2/">Post Title B</a></div>   
4 - </div>  

1 - <div style="width:25%; float:left; padding:10px; display:block;">       
2 - <div><img src="/wp-content/uploads/Thumbnail-Image-150x150.gif" style="display:block; width:100%;"></div>       
3 - <div><a href="/roundup/post3/">Post Title C</a></div>   
4 - </div>  

1 - <div style="width:25%; float:left; padding:10px; display:block;">       
2 - <div><img src="/wp-content/uploads/SnacksTHUMBNAIL-150x150.jpg" style="display:block; width:100%;"></div>       
3 - <div><a href="/roundup/post4/">Post Title D</a></div>   
4 - </div>

End -> </div>

输出如果使用&#34;返回&#34;在功能 - 输出是坏/坏

开始 - &gt;

1 - <div style="width:25%; float:left; padding:10px; display:block;">       
2 - <div><img src="/wp-content/uploads/THUMBNAIL-150x150.jpg" style="display:block; width:100%;"></div>     
3 - <div></div>     
3 - <div></div>     
3 - <div><a href="/roundup/post3/">Post Title C</div>   
4 - </div>  

1 - <div style="width:25%; float:left; padding:10px; display:block;">       
2 - <div><img src="/wp-content/uploads/SnacksTHUMBNAIL-150x150.jpg" style="display:block; width:100%;"></div>       
3 - <div><a href="/roundup/post4/">Post Title D</div>   
4 - </div>

End -> </div>

3 个答案:

答案 0 :(得分:1)

有几个问题。让我们来谈谈它们。

  1. 您需要在密钥count周围加上宽度等式的引号,即$atts['count'];
  2. 您希望在WordPress中使用转义清理程序,而不仅仅使用htmlentities
  3. 您需要在返回之前重置查询。最佳做法是将其放在foreach
  4. 之后
  5. 短代码必须返回而不是回声。它们使用do_shortcode()或处理内容时进行处理。
  6. 修订代码

    这是修改后的代码,它实现了上述功能。我在沙箱网站上测试了这段代码,它没有问题。

    add_shortcode( 'v3grid', 'v3grid_shortcode_processing' );
    /**
     * v3grid shortcode processor.  It builds the HTML markup for
     * the most recent posts and assembles them into a grid markup
     * structure.
     *
     * @since 1.0.0
     *
     * @param array $atts Array of user-defined attributes
     *
     * @return string
     */
    function v3grid_shortcode_processing( $atts ) {
    
        $atts = shortcode_atts(
            array(
                'count'       => 3,
                'link_to_all' => 'yes',
                'css_class'   => 'v3grid',
                'categories'  => '1',
            ), $atts, 'v3grid'
        );
    
        // Get list of recent posts
        $args = array(
            'numberposts' => (int) $atts['count'],
            'post_type'   => 'roundup',
            'post_status' => 'publish',
        );
    
        $recent_posts = wp_get_recent_posts( $args, ARRAY_A );
        if ( ! $recent_posts ) {
            return '<p>Sorry, there are no posts to display.</p>';
        }
    
        // Figure out width requirement for each grid item
        $width = 100 / (int) $atts['count'];
    
        // Container for row start
        $output = 'Start -> <div style="margin:0 -10px 0 -10px; box-sizing: border-box; position:relative; display:block;">';
    
        // Loop through posts
        foreach ( $recent_posts as $recent ) {
            $thumbnail = get_the_post_thumbnail_url( $recent["ID"], 'full' );
            $url       = get_permalink( $recent["ID"] );
    
            $output .= '   1 - <div style="width:' . (int) $width . '%; float:left; padding:10px; display:block;">';
            $output .= '       2 - <div><img src="' . esc_url( $thumbnail ) . '" style="display:block; width:100%;"></div>';
            $output .= '       3 - <div><a href="' . esc_url( $url ) . '">' . esc_html( $recent["post_title"] ) . '</a></div>';
            $output .= '   4 - </div>';
        }
        wp_reset_query();
    
        $output .= 'End -> </div>';
    
        return $output;
    }
    

    现在怎么办?

    现在您已修复了短代码功能中的问题。好的,但是你说原来的问题是:当你echo时它完全有效,但return却没有。这意味着在您返回HTML文本后会过滤掉某些内容。

    右?如果HTML在回显时是完美的,但在通过网站处理并呈现到浏览器中时很难,那么您知道问题的剩余部分可能是在上面的代码之后。

    我从查看你的插件开始。确保您没有执行此类过滤the_content。禁用插件的其余代码,看看短代码是否正确呈现。

    如果没有解决问题,请禁用所有其他插件。这个问题会消失吗?切换到默认的WordPress主题。这个问题会消失吗?

    这种方法就是我们所说的消除方法。您正在消除所有变量和可能的贡献者,将网站剥离到骨架以寻找根本原因。

    正如我所说,它在我的沙箱机器上没有问题。但我的设置与你的设置不一样。将网站剥离到最基本的必需品可以帮助您嗅出导致问题的原因。

    改进提示

    以下列出了一些可以帮助您的改进:

    1. 您不需要将传递给wp_get_recent_posts()的参数包含在默认状态元素中。请注意,我在上面的代码中减少了它们。
    2. 您想验证wp_get_recent_posts是否返回falsey。这意味着没有符合您标准的帖子。
    3. 执行shortcode_atts时包含短代码名称。虽然这不会导致您的问题,但允许其他开发人员访问是一种更好的做法。
    4. 使用类属性并将内联样式移动到样式表中。
    5. 关注点分离

      从PHP业务逻辑中删除HTML是最佳做法。将HTML放入视图文件中。为什么?关注点分离。它还提高了可读性。

      以下是您的一个例子。

      这是视图文件。我们称之为views/v3grid.php。请注意,它是原生HTML,因此更容易阅读。

      <!-- Start v3grid -->
      <div style="margin:0 -10px 0 -10px; box-sizing: border-box; position:relative; display:block;">
      <?php foreach ( $recent_posts as $recent ) :
          $thumbnail = get_the_post_thumbnail_url( $recent["ID"], 'full' ); ?>
          <!-- v3grid item -->
          <div class="v3grid--item" style="width: <?php echo (int) $width; ?>%; float: left; padding: 10px; display: block;">
              <div class="v3grid--thumbnail">
                  <img src="<?php echo esc_url( $thumbnail ); ?>" style="display: block; width: 100%;">
              </div>
              <div class="v3grid--entry-title">
                  <a href="<?php echo esc_url( get_permalink( $recent["ID"] ) ); ?>"><?php esc_html_e( $recent["post_title"] ); ?></a>
              </div>
          </div>
      <?php endforeach; ?>
      <!-- End v3grid --></div>
      

      然后在你的短代码函数中,你将这样的代码替换为:

      add_shortcode( 'v3grid', 'v3grid_shortcode_processing' );
      /**
       * v3grid shortcode processor.  It builds the HTML markup for
       * the most recent posts and assembles them into a grid markup
       * structure.
       *
       * @since 1.0.0
       *
       * @param array $atts Array of user-defined attributes
       *
       * @return string
       */
      function v3grid_shortcode_processing( $atts ) {
      
          .. this all remains the same as above
      
          // Figure out width requirement for each grid item
          $width = 100 / (int) $atts['count'];
      
          ob_start();
          include( __DIR__ .'/views/v3grid.php' );
          $html = ob_get_clean();
      
          wp_reset_query();
      
          return $html;
      }
      

      然后,您可以拉出所有内联样式并将它们添加到外部样式表中。

答案 1 :(得分:0)

在撰写shortcode时,您return在其功能中,并在您使用的.php文件中调用它:echo do_shortcode()

考虑使用通常的回显功能,除非它应该由插件用户通过仪表板使用。

答案 2 :(得分:0)

正如manual所说:

  

如果短代码产生大量HTML,那么ob_start可用于捕获输出并将其转换为字符串[...]

因此,您的代码必须使用echo并返回生成的字符串:

function v3grid_func() {
    ob_start(); // open the buffer

    /**
       all your code
    **/

    echo $output; // as you did

    return ob_get_clean(); // return from buffer and clean the buffer
}