如何解析嵌套的短码?

时间:2013-12-04 作者:jay

嵌套的短代码无法正确分析:

[row]
    [col size="6"]...[/col]
    [col size="6"]
        [row]
            [col size="6"]...[/col]
            [col size="6"]...[/col]
        [/row]
    [/col]
[/row]
WordPress documentation, 我知道这是WordPress短代码的限制。还有可能让它工作吗?

Edit:这是我的短码代码,如果它没有嵌套(即,行短码没有在列短码中使用),那么它可以正常工作。

add_shortcode( \'row\', \'row_cb\' );
function row_cb( $atts, $content = null ) {             
        $output = \'\';
        $output .= \'<div class="row">\';
        $output .= do_shortcode( $content );        
        $output .= \'</div>\';

        return $output; 
}

add_shortcode( \'col\', \'col_cb\' );
function col_cb( $atts, $content = null ) {     
    extract( shortcode_atts( array(
            \'size\'  => \'\',
        ), $atts ) );


    $output = \'\';
    $output .= \'<div class="col">\';
    $output .= do_shortcode( $content );        
    $output .= \'</div>\';

    return $output; 
}

3 个回复
SO网友:Unix

实际上,有一个解决方案。您使用的快捷码包含变量$content,而不包含筛选器do_shortcode, 像这样:

do_shortcode($content)
打开存在短代码的文件,并将$内容更改为do\\u短代码($内容)。它会起作用的。

SO网友:Olga Farber

我为嵌套的短代码创建了一个解决方案,也许您可以从中使用一些东西。

我使用了递归正则表达式(注意|(?R)), 因此,它可能没有官方的do\\u短代码快,但它允许用相同的名称嵌套短代码。

我的要求是没有固定的短代码列表(因此必须解析内容短代码中存在的所有短代码),以允许任何级别的嵌套,并且使用$atts的结构,其中包含一些参数,在填充此确切内容时存在。

对于$atts,我也编写了自己的函数,因为我希望$atts包含来自内容的所有内容(而不仅仅是那些定义了默认值的内容),以及这些字段的默认值,这些字段存在于默认数组中,而不是来自短码值。

以下是我的atts功能:

function complete_atts_with_defaults( $pairs, $atts = array() ) {
  $out = $atts;
  foreach ($pairs as $name => $default) {
    if ( array_key_exists($name, $atts)  && !empty( $atts[$name] ) ) { continue; }
    //else
    $out[$name] = $default;
  }
  return $out;
}
下面是另一个代码:

define( \'OUR_SHORTCODE_FULL_REGEX\', \'@\\[([a-z0-9_]+)([^\\]]*)\\]((?:[^[]|(?R))+)\\[\\/\\1\\]@\' );
define( \'OUR_SHORTCODE_HALF_REGEX\', \'@\\[([a-z0-9_]+)([^\\]]*)\\/\\]@\' );

function fill_all_post_placeholders( $text, $atts = array() ) {
  //...
  $text = str_replace( \'%5B\', \'[\', $text );
  $text = str_replace( \'%5D\', \']\', $text );

  $atts = complete_atts_with_defaults(
        array(
            \'value1\' => \'Hi :)\',
            \'value2\' => \'\',
            \'value3\' => \'\',
        ), $atts );

  //...

  $text = preg_replace_callback( OUR_SHORTCODE_HALF_REGEX, function( $match ) use ( $atts ) { return replace_half_shortcode_placeholder( $match[1], $match[2], $atts ); }, $text );
  $text = preg_replace_callback( OUR_SHORTCODE_FULL_REGEX, function( $match ) use ( $atts ) { return replace_shortcode_placeholder( $match[1], $match[2], $match[3], $atts ); }, $text );

  return $text;
}

function replace_shortcode_placeholder( $name, $params, $content, $atts ) {
  $content = preg_replace_callback( OUR_SHORTCODE_FULL_REGEX, function( $match ) use ( $atts ) { return replace_shortcode_placeholder( $match[1], $match[2], $match[3], $atts ); }, $content );
  //   $function_to_call = \'_rp_\' . $name;
  //   if ( function_exists( $function_to_call ) ) { return $function_to_call( $name, $params, $atts ); }
  //   //else
  //   $value = $atts[ $name ];
  //   if ( empty( $value ) ) { return \'\'; }
  //   //else
  //   return $value;

  return \'<br>name: \'  . $name . \' <br>params: \' . $params . \' <br>content: (\' . $content . \')<br><br>\';
}

function replace_half_shortcode_placeholder( $name, $params, $atts ) {
  //   $function_to_call = \'_rp_\' . $name;
  //   if ( function_exists( $function_to_call ) ) { return $function_to_call( $name, $params, $atts ); }
  //   //else
  //   $value = $atts[ $name ];
  //   if ( empty( $value ) ) { return \'\'; }
  //   //else
  //   return $value;

  return \'<br>name half: \'  . $name . \' <br>params half: \' . $params . \'<br><br>\';
}
我为您保留了完整的注释区域,以便您可以看到如何使用这些函数。

我的这些“短代码”没有注册,正如您在注释代码中看到的那样,它们的工作方式是不同的,动态的。

此外,这些短代码工作的必要规则是,始终向自动关闭标记添加“/”,就像在XML中一样。(在代码中,它们被称为“半短码”。)

此代码解析的内容示例(抱歉,这是胡言乱语):

[show_text_if campaign="2899"]subscribing to this newsletter [show_text_if campaign="2901" field_value="\'a href=\'http://ajshdash.com/asdhal/asdasdasd\'" field_value2="айксчд асй даксчй д"]subscribing to this new newsletter[/show_text_if] [red value1="dfsdfs" value2="sdfkls dfh skjha skd"/][/show_text_if]

[color value3="askdfjajls" value4="lskdfhjsldhfs df"/]

[show_text_if_not campaign="2899"]asdklja slkd alkd alskdj alsjd alsj als jdalsk jals dalskj asjd <a href="http://example.com/experiment/" target="_blank">Experiment</a> once more hooray! [green value4="askljjlaskd"/] Я сегодня это Я и я! :)[/show_text_if_not]

[show_text_if field_name="campaign" field_value="2899"]slkjd alsjkd aljsd ajs d new[/show_text_if]
我理解,这段代码并不能直接解决您所要求的问题,但也许您可以使用其中的一部分,自己解决问题。

SO网友:gmazzap

您的快捷码回调应显示如下所示:

add_shortcode(\'col\', \'col_cb\');

add_shortcode(\'row\', \'row_cb\');

function col_cb( $atts, $content ) {
  $content = do_shortcode($content);
  // ...
}

function row_cb( $atts, $content ) {
  $content = do_shortcode($content);
  // ...
}

结束

相关推荐

get data with shortcode

我有一个wp db。我添加了一个表“wp\\u mapmus”现在我想在贴子页面上用短代码显示这些数据。但有一个错误。我对php不太了解。我只使用相同的插件。正确的代码是什么?我的代码:function veri_cek($atts, $content = null) { extract( shortcode_atts( array( \'id\' => \'0\', ), $atts ) ); global $wpdb; $table = $wpdb-&g